mirror of
https://github.com/scinote-eln/scinote-web.git
synced 2025-09-05 20:54:27 +08:00
Merge branch 'decoupling-settings-page' into td_SCI_1565
This commit is contained in:
commit
989be6563f
20 changed files with 270 additions and 77 deletions
|
@ -2,9 +2,6 @@ module ClientApi
|
|||
class TeamsController < ApplicationController
|
||||
MissingTeamError = Class.new(StandardError)
|
||||
|
||||
# TODO remove this when the user authentication will be implemented
|
||||
skip_before_action :verify_authenticity_token
|
||||
|
||||
def index
|
||||
success_response
|
||||
end
|
||||
|
|
|
@ -4,6 +4,7 @@ export const GET_LIST_OF_TEAMS = "GET_LIST_OF_TEAMS";
|
|||
|
||||
// activities
|
||||
export const GLOBAL_ACTIVITIES_DATA = "GLOBAL_ACTIVITIES_DATA";
|
||||
export const DESTROY_GLOBAL_ACTIVITIES_DATA = "DESTROY_GLOBAL_ACTIVITIES_DATA";
|
||||
|
||||
// users
|
||||
export const SET_CURRENT_USER = "SET_CURRENT_USER";
|
||||
|
|
7
app/javascript/packs/app/axios.js
Normal file
7
app/javascript/packs/app/axios.js
Normal file
|
@ -0,0 +1,7 @@
|
|||
import axios from "axios";
|
||||
|
||||
export default axios.create({
|
||||
headers: {
|
||||
"X-CSRF-TOKEN": document.querySelector('meta[name="csrf-token"]').content
|
||||
}
|
||||
});
|
|
@ -6,6 +6,10 @@ export const DARK_GRAY_COLOR = "#7a7a7a";
|
|||
export const BORDER_LIGHT_COLOR = "#e3e3e3";
|
||||
export const WILD_SAND_COLOR = "#f5f5f5";
|
||||
export const MYSTIC_COLOR = "#eaeff2";
|
||||
export const COLOR_CONCRETE = "#f2f2f2";
|
||||
export const COLOR_MINE_SHAFT = "#333"
|
||||
export const COLOR_BLACK = "#000";
|
||||
export const COLOR_GRAY_LIGHT_YADCF = "#ccc";
|
||||
export const ICON_GREEN_COLOR = "#8fd13f";
|
||||
export const NOTIFICATION_YES = "#5a8921";
|
||||
export const NOTIFICATION_YES_BORDER = "#4d751c";
|
||||
|
|
|
@ -8,7 +8,14 @@ export default {
|
|||
loading: "Loading ..."
|
||||
},
|
||||
navbar: {
|
||||
page_title: "sciNote"
|
||||
page_title: "sciNote",
|
||||
home_label: "Home",
|
||||
protocols_label: "Protocols",
|
||||
repositories_label: "Repositories",
|
||||
activities_label: "Activities",
|
||||
search_label: "Search",
|
||||
notifications_label: "Notifications",
|
||||
info_label: "Info"
|
||||
},
|
||||
settings_page: {
|
||||
account: "Account",
|
||||
|
|
|
@ -1,6 +1,9 @@
|
|||
import axios from "axios";
|
||||
import axios from "../../app/axios";
|
||||
import { ACTIVITIES_PATH } from "../../app/routes";
|
||||
import { GLOBAL_ACTIVITIES_DATA } from "../../app/action_types";
|
||||
import {
|
||||
GLOBAL_ACTIVITIES_DATA,
|
||||
DESTROY_GLOBAL_ACTIVITIES_DATA
|
||||
} from "../../app/action_types";
|
||||
|
||||
function addActivitiesData(data) {
|
||||
return {
|
||||
|
@ -9,9 +12,15 @@ function addActivitiesData(data) {
|
|||
};
|
||||
}
|
||||
|
||||
export function getActivities(last_id = 0) {
|
||||
export function destroyActivities() {
|
||||
return {
|
||||
type: DESTROY_GLOBAL_ACTIVITIES_DATA
|
||||
};
|
||||
}
|
||||
|
||||
export function getActivities(lastId = 0) {
|
||||
return dispatch => {
|
||||
let path = `${ACTIVITIES_PATH}?from=${last_id}`;
|
||||
const path = `${ACTIVITIES_PATH}?from=${lastId}`;
|
||||
axios
|
||||
.get(path, { withCredentials: true })
|
||||
.then(response => {
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import axios from "axios";
|
||||
import axios from "../../app/axios";
|
||||
import _ from "lodash";
|
||||
import { TEAMS_PATH, CHANGE_TEAM_PATH } from "../../app/routes";
|
||||
import { GET_LIST_OF_TEAMS, SET_CURRENT_TEAM } from "../../app/action_types";
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import axios from "axios";
|
||||
import axios from "../../app/axios";
|
||||
import { CURRENT_USER_PATH } from "../../app/routes";
|
||||
import {
|
||||
SET_CURRENT_USER,
|
||||
|
|
|
@ -1,11 +1,34 @@
|
|||
import React from "react";
|
||||
import PropTypes from "prop-types";
|
||||
import { FormattedDate } from "react-intl";
|
||||
import Moment from "react-moment";
|
||||
import styled from "styled-components";
|
||||
|
||||
import { WHITE_COLOR } from "../../../app/constants/colors"
|
||||
|
||||
const StyledLi = styled.li`
|
||||
margin-bottom: 1em;
|
||||
`
|
||||
|
||||
const StyledSpan = styled.span`
|
||||
display: inline;
|
||||
padding: 5px 30px;
|
||||
font-size: 1em;
|
||||
font-weight: bold;
|
||||
line-height: 1;
|
||||
color: ${WHITE_COLOR};
|
||||
white-space: nowrap;
|
||||
vertical-align: baseline;
|
||||
border-radius: .25em;
|
||||
`;
|
||||
|
||||
const ActivityDateElement = ({ date }) =>
|
||||
<li className="data-element">
|
||||
<FormattedDate value={date} day="2-digit" month="2-digit" year="numeric" />
|
||||
</li>;
|
||||
<StyledLi className="text-center">
|
||||
<StyledSpan className="label label-primary">
|
||||
<Moment format="DD.MM.YYYY">
|
||||
{date}
|
||||
</Moment>
|
||||
</StyledSpan>
|
||||
</StyledLi>;
|
||||
|
||||
ActivityDateElement.propTypes = {
|
||||
date: PropTypes.instanceOf(Date).isRequired
|
||||
|
|
|
@ -1,24 +1,54 @@
|
|||
import React from "react";
|
||||
import PropTypes from "prop-types";
|
||||
import { FormattedTime } from "react-intl";
|
||||
import Moment from "react-moment";
|
||||
import styled from "styled-components";
|
||||
|
||||
import {
|
||||
WHITE_COLOR,
|
||||
COLOR_CONCRETE,
|
||||
BORDER_GRAY_COLOR
|
||||
} from "../../../app/constants/colors";
|
||||
|
||||
const StyledLi = styled.li`
|
||||
border-radius: .25em;
|
||||
margin-bottom: 1em;
|
||||
background-color: ${WHITE_COLOR};
|
||||
border: 1px solid ${COLOR_CONCRETE};
|
||||
`;
|
||||
const TimeSpan = styled.span`
|
||||
min-width: 150px;
|
||||
display: table-cell;
|
||||
vertical-align: middle;
|
||||
border-top-left-radius: .25em;
|
||||
border-bottom-left-radius: .25em;
|
||||
border: 3px solid ${BORDER_GRAY_COLOR};
|
||||
background-color: ${BORDER_GRAY_COLOR};
|
||||
padding-left: 10px;
|
||||
padding-right: 10px;
|
||||
vertical-align: top;
|
||||
`;
|
||||
|
||||
const TextSpan = styled.span`
|
||||
display: table-cell;
|
||||
padding: 3px 10px;
|
||||
text-align: justify;
|
||||
`
|
||||
|
||||
const ActivityElement = ({ activity }) =>
|
||||
<li>
|
||||
<span>
|
||||
<FormattedTime
|
||||
value={activity.created_at}
|
||||
hour="numeric"
|
||||
minute="numeric"
|
||||
/>
|
||||
</span>
|
||||
<span dangerouslySetInnerHTML={{ __html: activity.message }} />
|
||||
</li>;
|
||||
<StyledLi>
|
||||
<TimeSpan>
|
||||
<Moment format="HH.mm">
|
||||
{activity.created_at}
|
||||
</Moment>
|
||||
</TimeSpan>
|
||||
<TextSpan dangerouslySetInnerHTML={{ __html: activity.message }} />
|
||||
</StyledLi>;
|
||||
|
||||
ActivityElement.propTypes = {
|
||||
activity: PropTypes.shape({
|
||||
message: PropTypes.string.isRequired,
|
||||
created_at: PropTypes.string.isRequired
|
||||
})
|
||||
}).isRequired
|
||||
};
|
||||
|
||||
export default ActivityElement;
|
||||
|
|
|
@ -4,10 +4,46 @@ import PropTypes from "prop-types";
|
|||
import { FormattedMessage } from "react-intl";
|
||||
import { Modal, Button } from "react-bootstrap";
|
||||
import _ from "lodash";
|
||||
import styled from "styled-components";
|
||||
|
||||
import { getActivities } from "../../actions/ActivitiesActions";
|
||||
import ActivityElement from "./ActivityElement";
|
||||
import ActivityDateElement from "./ActivityDateElement";
|
||||
import {
|
||||
WHITE_COLOR,
|
||||
COLOR_CONCRETE,
|
||||
COLOR_MINE_SHAFT,
|
||||
COLOR_GRAY_LIGHT_YADCF
|
||||
} from "../../../app/constants/colors";
|
||||
|
||||
const StyledBottom = styled(Button)`
|
||||
display: inline-block;
|
||||
margin-bottom: 0;
|
||||
font-weight: normal;
|
||||
text-align: center;
|
||||
vertical-align: middle;
|
||||
touch-action: manipulation;
|
||||
cursor: pointer;
|
||||
background-image: none;
|
||||
border: 1px solid transparent;
|
||||
white-space: nowrap;
|
||||
padding: 6px 12px;
|
||||
font-size: 14px;
|
||||
line-height: 1.42857143;
|
||||
border-radius: 4px;
|
||||
-webkit-user-select: none;
|
||||
-moz-user-select: none;
|
||||
-ms-user-select: none;
|
||||
user-select: none;
|
||||
color: ${COLOR_MINE_SHAFT};
|
||||
background-color: ${WHITE_COLOR};
|
||||
border-color: ${COLOR_GRAY_LIGHT_YADCF};
|
||||
`;
|
||||
|
||||
const StyledModalBody = styled(Modal.Body)`
|
||||
background-color: ${COLOR_CONCRETE};
|
||||
color: ${COLOR_MINE_SHAFT};;
|
||||
`;
|
||||
|
||||
class GlobalActivitiesModal extends Component {
|
||||
constructor(props) {
|
||||
|
@ -25,9 +61,9 @@ class GlobalActivitiesModal extends Component {
|
|||
);
|
||||
}
|
||||
return this.props.activities.map((activity, i, arr) => {
|
||||
let newDate = new Date(activity.created_at);
|
||||
const newDate = new Date(activity.created_at);
|
||||
if (i > 0) {
|
||||
let prevDate = new Date(arr[i - 1].created_at);
|
||||
const prevDate = new Date(arr[i - 1].created_at);
|
||||
if (prevDate < newDate) {
|
||||
return [
|
||||
<ActivityDateElement key={newDate} date={newDate} />,
|
||||
|
@ -45,20 +81,21 @@ class GlobalActivitiesModal extends Component {
|
|||
}
|
||||
|
||||
addMoreActivities() {
|
||||
let last_id = _.last(this.props.activities).id;
|
||||
this.props.fetchActivities(last_id);
|
||||
const lastId = _.last(this.props.activities).id;
|
||||
this.props.fetchActivities(lastId);
|
||||
}
|
||||
|
||||
addMoreButton() {
|
||||
if (this.props.more) {
|
||||
return (
|
||||
<li>
|
||||
<Button onClick={this.addMoreActivities}>
|
||||
<li className="text-center">
|
||||
<StyledBottom onClick={this.addMoreActivities}>
|
||||
<FormattedMessage id="activities.more_activities" />
|
||||
</Button>
|
||||
</StyledBottom>
|
||||
</li>
|
||||
);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
render() {
|
||||
|
@ -69,12 +106,12 @@ class GlobalActivitiesModal extends Component {
|
|||
<FormattedMessage id="activities.modal_title" />
|
||||
</Modal.Title>
|
||||
</Modal.Header>
|
||||
<Modal.Body>
|
||||
<ul>
|
||||
<StyledModalBody>
|
||||
<ul className="list-unstyled">
|
||||
{this.displayActivities()}
|
||||
{this.addMoreButton()}
|
||||
</ul>
|
||||
</Modal.Body>
|
||||
</StyledModalBody>
|
||||
<Modal.Footer>
|
||||
<Button onClick={this.props.onCloseModal}>
|
||||
<FormattedMessage id="general.close" />
|
||||
|
@ -100,13 +137,13 @@ GlobalActivitiesModal.propTypes = {
|
|||
};
|
||||
|
||||
const mapStateToProps = ({ global_activities }) => {
|
||||
let { activities, more } = global_activities;
|
||||
const { activities, more } = global_activities;
|
||||
return { activities, more };
|
||||
};
|
||||
|
||||
const mapDispatchToProps = dispatch => ({
|
||||
fetchActivities(last_id) {
|
||||
dispatch(getActivities(last_id));
|
||||
fetchActivities(lastId) {
|
||||
dispatch(getActivities(lastId));
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -12,7 +12,14 @@ import {
|
|||
const InfoDropdown = () =>
|
||||
<NavDropdown
|
||||
noCaret
|
||||
title={<span className="glyphicon glyphicon-info-sign" />}
|
||||
title={
|
||||
<span>
|
||||
<span className="glyphicon glyphicon-info-sign" />
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.info_label" />
|
||||
</span>
|
||||
</span>
|
||||
}
|
||||
id="nav-info-dropdown"
|
||||
>
|
||||
<MenuItem href={CUSTOMER_SUPPORT_LINK} target="_blank">
|
||||
|
|
|
@ -83,7 +83,14 @@ class NotificationsDropdown extends Component {
|
|||
<StyledNavDropdown
|
||||
noCaret
|
||||
id="notifications-dropdown"
|
||||
title={<i className="fa fa-bell" />}
|
||||
title={
|
||||
<span>
|
||||
<i className="fa fa-bell" />
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.notifications_label" />
|
||||
</span>
|
||||
</span>
|
||||
}
|
||||
onClick={this.getRecentNotifications}
|
||||
>
|
||||
<StyledListHeader>
|
||||
|
|
|
@ -7,6 +7,7 @@ import {
|
|||
Glyphicon
|
||||
} from "react-bootstrap";
|
||||
import styled from "styled-components";
|
||||
import { FormattedMessage } from "react-intl";
|
||||
import { SEARCH_PATH } from "../../../app/routes";
|
||||
import { ENTER_KEY_CODE } from "../../../app/constants/numeric";
|
||||
|
||||
|
@ -60,7 +61,14 @@ class SearchDropdown extends Component {
|
|||
return (
|
||||
<StyledNavDropdown
|
||||
noCaret
|
||||
title={<span className="glyphicon glyphicon-search" />}
|
||||
title={
|
||||
<span>
|
||||
<span className="glyphicon glyphicon-search" />
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.search_label" />
|
||||
</span>
|
||||
</span>
|
||||
}
|
||||
onClick={this.setFocusToInput}
|
||||
id="search-dropdown"
|
||||
>
|
||||
|
|
|
@ -2,13 +2,14 @@ import React, { Component } from "react";
|
|||
import PropTypes from "prop-types";
|
||||
import { connect } from "react-redux";
|
||||
import { Navbar, Nav, NavItem } from "react-bootstrap";
|
||||
import { FormattedMessage } from "react-intl";
|
||||
import styled from "styled-components";
|
||||
import {
|
||||
MAIN_COLOR_BLUE,
|
||||
WHITE_COLOR,
|
||||
BORDER_GRAY_COLOR
|
||||
} from "../../app/constants/colors";
|
||||
import { getActivities } from "../actions/ActivitiesActions";
|
||||
import { getActivities, destroyActivities } from "../actions/ActivitiesActions";
|
||||
import TeamSwitch from "./components/TeamSwitch";
|
||||
import GlobalActivitiesModal from "./components/GlobalActivitiesModal";
|
||||
import SearchDropdown from "./components/SearchDropdown";
|
||||
|
@ -43,23 +44,36 @@ class Navigation extends Component {
|
|||
this.state = {
|
||||
showActivitesModal: false,
|
||||
page: "",
|
||||
currentTeam: { id: 0 }
|
||||
current_team: { id: 0 }
|
||||
};
|
||||
this.selectItemCallback = this.selectItemCallback.bind(this);
|
||||
this.closeModalCallback = this.closeModalCallback.bind(this);
|
||||
}
|
||||
|
||||
selectItemCallback(key, ev) {
|
||||
if (key === 4) {
|
||||
ev.preventDefault();
|
||||
this.setState({ showActivitesModal: !this.state.showActivitesModal });
|
||||
// Call action creator to fetch activities from the server
|
||||
this.props.fetchActivities();
|
||||
switch (key) {
|
||||
case 1:
|
||||
window.location = "/";
|
||||
break;
|
||||
case 2:
|
||||
window.location = "/protocols";
|
||||
break;
|
||||
case 3:
|
||||
window.location = `/teams/${this.props.current_team.id}/repositories`;
|
||||
break;
|
||||
case 4:
|
||||
ev.preventDefault();
|
||||
this.setState({ showActivitesModal: !this.state.showActivitesModal });
|
||||
// Call action creator to fetch activities from the server
|
||||
this.props.fetchActivities();
|
||||
break;
|
||||
default:
|
||||
}
|
||||
}
|
||||
|
||||
closeModalCallback() {
|
||||
this.setState({ showActivitesModal: false });
|
||||
this.props.destroyActivities();
|
||||
}
|
||||
|
||||
render() {
|
||||
|
@ -74,30 +88,39 @@ class Navigation extends Component {
|
|||
</Navbar.Brand>
|
||||
</Navbar.Header>
|
||||
<Nav>
|
||||
<NavItem eventKey={1} href="/">
|
||||
<span className="glyphicon glyphicon-home" title="Home" />
|
||||
<NavItem eventKey={1}>
|
||||
<span className="glyphicon glyphicon-home" title="Home" />
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.home_label" />
|
||||
</span>
|
||||
</NavItem>
|
||||
<NavItem eventKey={2} href="/protocols">
|
||||
<NavItem eventKey={2}>
|
||||
<span
|
||||
className="glyphicon glyphicon-list-alt"
|
||||
title="Protocol repositories"
|
||||
/>
|
||||
/>
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.protocols_label" />
|
||||
</span>
|
||||
</NavItem>
|
||||
<NavItem
|
||||
eventKey={3}
|
||||
href={`/teams/${this.state.currentTeam.id}/repositories`}
|
||||
>
|
||||
<NavItem eventKey={3}>
|
||||
<i
|
||||
className="fa fa-cubes"
|
||||
aria-hidden="true"
|
||||
title="Repositories"
|
||||
/>
|
||||
/>
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.repositories_label" />
|
||||
</span>
|
||||
</NavItem>
|
||||
<NavItem eventKey={4}>
|
||||
<span
|
||||
className="glyphicon glyphicon-equalizer"
|
||||
title="Activities"
|
||||
/>
|
||||
/>
|
||||
<span className="visible-xs-inline visible-sm-inline">
|
||||
<FormattedMessage id="navbar.activities_label" />
|
||||
</span>
|
||||
</NavItem>
|
||||
</Nav>
|
||||
<Nav pullRight>
|
||||
|
@ -118,14 +141,26 @@ class Navigation extends Component {
|
|||
}
|
||||
|
||||
Navigation.propTypes = {
|
||||
fetchActivities: PropTypes.func.isRequired
|
||||
fetchActivities: PropTypes.func.isRequired,
|
||||
destroyActivities: PropTypes.func.isRequired,
|
||||
current_team: PropTypes.shape({
|
||||
id: PropTypes.number.isRequired,
|
||||
name: PropTypes.string.isRequired,
|
||||
current_team: PropTypes.bool.isRequired
|
||||
}).isRequired
|
||||
};
|
||||
|
||||
// Map the fetch activity action to component
|
||||
// Map the states from store to component props
|
||||
const mapStateToProps = ({ current_team }) => ({ current_team });
|
||||
|
||||
// Map the fetch activity action to component props
|
||||
const mapDispatchToProps = dispatch => ({
|
||||
fetchActivities() {
|
||||
dispatch(getActivities());
|
||||
},
|
||||
destroyActivities() {
|
||||
dispatch(destroyActivities());
|
||||
}
|
||||
});
|
||||
|
||||
export default connect(null, mapDispatchToProps)(Navigation);
|
||||
export default connect(mapStateToProps, mapDispatchToProps)(Navigation);
|
|
@ -1,21 +1,27 @@
|
|||
import {
|
||||
GLOBAL_ACTIVITIES_DATA,
|
||||
MORE_GLOBAL_ACTIVITIES
|
||||
DESTROY_GLOBAL_ACTIVITIES_DATA
|
||||
} from "../../app/action_types";
|
||||
|
||||
export function globalActivities(
|
||||
state = { more: true, activities: [] },
|
||||
action
|
||||
) {
|
||||
if (action.type === GLOBAL_ACTIVITIES_DATA) {
|
||||
return {
|
||||
...state,
|
||||
activities: [
|
||||
...state.activities,
|
||||
...action.payload.global_activities.activities
|
||||
],
|
||||
more: action.payload.global_activities.more
|
||||
};
|
||||
const initialStateu = { more: true, activities: [] };
|
||||
|
||||
export function globalActivities(state = initialStateu, action) {
|
||||
switch (action.type) {
|
||||
case GLOBAL_ACTIVITIES_DATA:
|
||||
return {
|
||||
...state,
|
||||
activities: [
|
||||
...state.activities,
|
||||
...action.payload.global_activities.activities
|
||||
],
|
||||
more: action.payload.global_activities.more
|
||||
};
|
||||
case DESTROY_GLOBAL_ACTIVITIES_DATA:
|
||||
return {
|
||||
...state,
|
||||
...initialStateu
|
||||
};
|
||||
default:
|
||||
return state;
|
||||
}
|
||||
return state;
|
||||
}
|
||||
|
|
|
@ -9,6 +9,10 @@ body {
|
|||
font-size: 13px;
|
||||
}
|
||||
|
||||
.label-primary {
|
||||
background-color: $color-theme-primary;
|
||||
}
|
||||
|
||||
.btn-primary {
|
||||
background-color: $color-theme-secondary;
|
||||
border-color: $primary-hover-color;
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
<meta data-hook="head-js">
|
||||
<title><%= t('nav.title') %></title>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no">
|
||||
<%= csrf_meta_tags %>
|
||||
<%= stylesheet_link_tag 'bootstrap/css/bootstrap.min' %>
|
||||
<%= stylesheet_link_tag 'font-awesome/css/font-awesome.min' %>
|
||||
<%= stylesheet_pack_tag 'styles/main' %>
|
||||
|
|
|
@ -53,6 +53,7 @@
|
|||
"glob": "^7.1.2",
|
||||
"js-yaml": "^3.9.0",
|
||||
"lodash": "^4.17.4",
|
||||
"moment": "^2.18.1",
|
||||
"node-sass": "^4.5.3",
|
||||
"path-complete-extname": "^0.1.0",
|
||||
"postcss-loader": "^2.0.6",
|
||||
|
@ -66,6 +67,7 @@
|
|||
"react-dom": "^15.6.1",
|
||||
"react-intl": "^2.3.0",
|
||||
"react-intl-redux": "^0.6.0",
|
||||
"react-moment": "^0.6.4",
|
||||
"react-redux": "^5.0.5",
|
||||
"react-router-bootstrap": "^0.24.2",
|
||||
"react-router-dom": "^4.1.2",
|
||||
|
|
|
@ -3572,6 +3572,10 @@ mkdirp@0.5.x, "mkdirp@>=0.5 0", mkdirp@^0.5.0, mkdirp@^0.5.1, mkdirp@~0.5.0, mkd
|
|||
dependencies:
|
||||
minimist "0.0.8"
|
||||
|
||||
moment@^2.18.1:
|
||||
version "2.18.1"
|
||||
resolved "https://registry.yarnpkg.com/moment/-/moment-2.18.1.tgz#c36193dd3ce1c2eed2adb7c802dbbc77a81b1c0f"
|
||||
|
||||
ms@2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/ms/-/ms-2.0.0.tgz#5608aeadfc00be6c2901df5f9861788de0d597c8"
|
||||
|
@ -4719,6 +4723,10 @@ react-intl@^2.3.0:
|
|||
intl-relativeformat "^1.3.0"
|
||||
invariant "^2.1.1"
|
||||
|
||||
react-moment@^0.6.4:
|
||||
version "0.6.4"
|
||||
resolved "https://registry.yarnpkg.com/react-moment/-/react-moment-0.6.4.tgz#5e531d47ad7b0bff6f6b7175093e98659f5e667b"
|
||||
|
||||
react-modal@^1.4.0:
|
||||
version "1.9.7"
|
||||
resolved "https://registry.yarnpkg.com/react-modal/-/react-modal-1.9.7.tgz#07ef56790b953e3b98ef1e2989e347983c72871d"
|
||||
|
|
Loading…
Add table
Reference in a new issue