mirror of
https://github.com/xodio/xod.git
synced 2026-03-23 09:06:55 +01:00
feat(xod-client,xod-client-browser,xod-client-electron): display compilation limits
This commit is contained in:
@@ -24,6 +24,7 @@ module.exports = {
|
||||
],
|
||||
|
||||
globals: {
|
||||
fetch: true,
|
||||
window: true,
|
||||
document: true,
|
||||
describe: true,
|
||||
|
||||
@@ -96,6 +96,7 @@ module.exports = {
|
||||
'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV || 'development'),
|
||||
'process.env.XOD_HM_DEF': JSON.stringify(process.env.XOD_HM_DEF || false),
|
||||
|
||||
'process.env.XOD_HOSTNAME': JSON.stringify(process.env.XOD_HOSTNAME || 'xod.io'),
|
||||
'process.env.XOD_SITE_DOMAIN': JSON.stringify(''),
|
||||
'process.env.XOD_FORUM_DOMAIN': JSON.stringify('https://forum.xod.io/'),
|
||||
'process.env.XOD_UTM_SOURCE': JSON.stringify('ide-browser'),
|
||||
|
||||
@@ -41,6 +41,7 @@ class PopupUploadConfig extends React.Component {
|
||||
this.getSelectedBoard()
|
||||
.then(selectedBoard => this.getBoards(selectedBoard));
|
||||
this.getPorts();
|
||||
this.props.updateCompileLimit();
|
||||
}
|
||||
|
||||
onClose() {
|
||||
@@ -252,6 +253,7 @@ class PopupUploadConfig extends React.Component {
|
||||
render() {
|
||||
const boards = this.renderBoardSelect();
|
||||
const ports = this.renderPortSelect();
|
||||
const compileLimitLeft = this.props.compileLimitLeft;
|
||||
|
||||
return (
|
||||
<PopupForm
|
||||
@@ -270,10 +272,14 @@ class PopupUploadConfig extends React.Component {
|
||||
id="compileInCloud"
|
||||
type="checkbox"
|
||||
checked={this.state.doCompileInCloud}
|
||||
disabled={compileLimitLeft <= 0}
|
||||
onChange={this.onCloudCompilationChanged}
|
||||
/>
|
||||
<label htmlFor="compileInCloud">
|
||||
Compile in the cloud (experimental)
|
||||
Compile in the cloud
|
||||
{compileLimitLeft
|
||||
? <span>({compileLimitLeft} left)</span>
|
||||
: <span>(currently offline)</span>}
|
||||
</label>
|
||||
</div>
|
||||
<div className="ModalContent">
|
||||
@@ -300,6 +306,8 @@ class PopupUploadConfig extends React.Component {
|
||||
PopupUploadConfig.propTypes = {
|
||||
isVisible: PropTypes.bool,
|
||||
selectedPort: PropTypes.object,
|
||||
compileLimitLeft: PropTypes.number,
|
||||
updateCompileLimit: PropTypes.func,
|
||||
getSelectedBoard: PropTypes.func,
|
||||
listBoards: PropTypes.func,
|
||||
listPorts: PropTypes.func,
|
||||
|
||||
@@ -227,6 +227,7 @@ class App extends client.App {
|
||||
}
|
||||
// Remove listener if process is finished.
|
||||
ipcRenderer.removeAllListeners(UPLOAD_TO_ARDUINO);
|
||||
this.props.actions.updateCompileLimit();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -549,6 +550,8 @@ class App extends client.App {
|
||||
selectedPort={this.props.selectedPort}
|
||||
listBoards={this.listBoards}
|
||||
listPorts={this.listPorts}
|
||||
compileLimitLeft={this.props.compileLimitLeft}
|
||||
updateCompileLimit={this.props.actions.updateCompileLimit}
|
||||
onBoardChanged={this.onArduinoTargetBoardChange}
|
||||
onPortChanged={this.onSerialPortChange}
|
||||
onUpload={this.onUploadToArduino}
|
||||
@@ -658,6 +661,7 @@ App.propTypes = R.merge(client.App.propTypes, {
|
||||
project: client.sanctuaryPropType(Project),
|
||||
actions: PropTypes.objectOf(PropTypes.func),
|
||||
upload: PropTypes.object,
|
||||
compileLimitLeft: PropTypes.number,
|
||||
workspace: PropTypes.string,
|
||||
selectedPort: PropTypes.object,
|
||||
});
|
||||
@@ -674,6 +678,7 @@ const mapStateToProps = R.applySpec({
|
||||
saveProcess: getSaveProcess,
|
||||
currentPatchPath: client.getCurrentPatchPath,
|
||||
selectedPort: getSelectedSerialPort,
|
||||
compileLimitLeft: client.getCompileLimitLeft,
|
||||
popups: {
|
||||
createProject: client.getPopupVisibility(client.POPUP_ID.CREATING_PROJECT),
|
||||
projectSelection: client.getPopupVisibility(client.POPUP_ID.OPENING_PROJECT),
|
||||
|
||||
@@ -110,6 +110,7 @@ const options = {
|
||||
'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV || 'development'),
|
||||
'process.env.XOD_HM_DEF': JSON.stringify(process.env.XOD_HM_DEF || false),
|
||||
|
||||
'process.env.XOD_HOSTNAME': JSON.stringify(process.env.XOD_HOSTNAME || 'xod.io'),
|
||||
'process.env.XOD_SITE_DOMAIN': JSON.stringify('https://xod.io/'),
|
||||
'process.env.XOD_FORUM_DOMAIN': JSON.stringify('https://forum.xod.io/'),
|
||||
'process.env.XOD_UTM_SOURCE': JSON.stringify('ide-desktop'),
|
||||
|
||||
@@ -35,3 +35,9 @@ is used. Reducers simply delegate state update to `xod-project`’s functions,
|
||||
selectors, and components use functions from `xod-project` to access project
|
||||
data. This distincion is done because project state is complex and keeping all
|
||||
machinery inside standard pod layout would make it messy.
|
||||
|
||||
## Environment variables
|
||||
|
||||
- **`XOD_HOSTNAME`**
|
||||
|
||||
XOD hostname. Default: `xod.io`
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
"font-awesome": "^4.6.3",
|
||||
"formsy-react": "^0.18.1",
|
||||
"formsy-react-components": "^0.8.1",
|
||||
"isomorphic-fetch": "^2.2.1",
|
||||
"prop-types": "^15.5.10",
|
||||
"ramda": "^0.24.1",
|
||||
"ramda-fantasy": "^0.7.0",
|
||||
|
||||
@@ -22,6 +22,7 @@ export const showCode = code => ({
|
||||
payload: { code },
|
||||
});
|
||||
|
||||
export * from '../user/actions';
|
||||
export * from '../editor/actions';
|
||||
export * from '../project/actions';
|
||||
export * from '../projectBrowser/actions';
|
||||
|
||||
@@ -29,6 +29,7 @@ export default class App extends React.Component {
|
||||
document.addEventListener('cut', this.props.actions.cutEntities);
|
||||
document.addEventListener('copy', this.props.actions.copyEntities);
|
||||
document.addEventListener('paste', this.props.actions.pasteEntities);
|
||||
this.props.actions.updateCompileLimit();
|
||||
}
|
||||
|
||||
onShowCodeArduino() {
|
||||
@@ -128,6 +129,7 @@ App.propTypes = {
|
||||
popups: PropTypes.objectOf(PropTypes.bool),
|
||||
popupsData: PropTypes.objectOf(PropTypes.object),
|
||||
actions: PropTypes.shape({
|
||||
updateCompileLimit: PropTypes.func.isRequired,
|
||||
createProject: PropTypes.func.isRequired,
|
||||
updateProjectMeta: PropTypes.func.isRequired,
|
||||
hideAllPopups: PropTypes.func.isRequired,
|
||||
@@ -163,6 +165,7 @@ App.propTypes = {
|
||||
};
|
||||
|
||||
App.actions = {
|
||||
updateCompileLimit: actions.updateCompileLimit,
|
||||
createProject: actions.createProject,
|
||||
requestCreateProject: actions.requestCreateProject,
|
||||
requestRenameProject: actions.requestRenameProject,
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import { merge } from 'ramda';
|
||||
import { combineReducers } from 'redux';
|
||||
|
||||
import userReducer from '../user/reducer';
|
||||
import projectReducer from '../project/reducer';
|
||||
import undoableProject from './undoableProject';
|
||||
import projectBrowserReducer from '../projectBrowser/reducer';
|
||||
@@ -15,6 +16,7 @@ import keepIntegrityAfterNavigatingHistory from './keepIntegrityAfterNavigatingH
|
||||
const combineRootReducers = (extraReducers) => {
|
||||
const reducers = merge(
|
||||
{
|
||||
user: userReducer,
|
||||
project: projectReducer,
|
||||
projectHistory: (s = {}) => s,
|
||||
projectBrowser: projectBrowserReducer,
|
||||
|
||||
@@ -4,6 +4,7 @@ import { createSelector } from 'reselect';
|
||||
|
||||
import * as XP from 'xod-project';
|
||||
|
||||
import * as User from '../user/selectors';
|
||||
import * as Editor from '../editor/selectors';
|
||||
import * as Project from '../project/selectors';
|
||||
import * as ProjectBrowser from '../projectBrowser/selectors';
|
||||
@@ -70,6 +71,7 @@ export const getPatchForHelpbar = createSelector(
|
||||
|
||||
|
||||
export default {
|
||||
User,
|
||||
Editor,
|
||||
Errors,
|
||||
Processes,
|
||||
|
||||
@@ -1,9 +1,11 @@
|
||||
import userState from '../user/state';
|
||||
import editorState from '../editor/state';
|
||||
import projectState from '../project/state';
|
||||
import debuggerState from '../debugger/state';
|
||||
import projectBrowserState from '../projectBrowser/state';
|
||||
|
||||
export default {
|
||||
user: userState,
|
||||
project: projectState,
|
||||
projectHistory: {},
|
||||
projectBrowser: projectBrowserState,
|
||||
|
||||
@@ -14,7 +14,7 @@ import Widgets, { WIDGET_MAPPING } from './inspectorWidgets';
|
||||
|
||||
import { RenderableNode } from '../../types';
|
||||
import sanctuaryPropType from '../../utils/sanctuaryPropType';
|
||||
import { getUtmSiteUrl } from '../../utils/siteLinks';
|
||||
import { getUtmSiteUrl } from '../../utils/urls';
|
||||
|
||||
import * as MESSAGES from '../messages';
|
||||
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import * as UserSelectors from './user/selectors';
|
||||
import * as EditorSelectors from './editor/selectors';
|
||||
import * as UtilsSelectors from './utils/selectors';
|
||||
import * as ProcessSelectors from './processes/selectors';
|
||||
@@ -22,7 +23,7 @@ import * as PopupConstants from './popups/constants';
|
||||
|
||||
import popupsReducer, { showOnlyPopup, hideOnePopup } from './popups/reducer';
|
||||
|
||||
import * as siteLinkUtils from './utils/siteLinks';
|
||||
import * as siteLinkUtils from './utils/urls';
|
||||
import * as BrowserUtils from './utils/browser';
|
||||
import * as MenuUtils from './utils/menu';
|
||||
import sanctuaryPropType from './utils/sanctuaryPropType';
|
||||
@@ -63,7 +64,7 @@ export * from './debugger/selectors';
|
||||
|
||||
export * from './utils/browser';
|
||||
export * from './utils/constants';
|
||||
export * from './utils/siteLinks';
|
||||
export * from './utils/urls';
|
||||
export * from './popups/constants';
|
||||
export { lowercaseKebabMask } from './utils/inputFormatting';
|
||||
export { default as sanctuaryPropType } from './utils/sanctuaryPropType';
|
||||
@@ -109,6 +110,7 @@ export default Object.assign({
|
||||
PopupProjectPreferences,
|
||||
TAB_CLOSE,
|
||||
},
|
||||
UserSelectors,
|
||||
UtilsSelectors,
|
||||
EditorSelectors,
|
||||
ProcessSelectors,
|
||||
|
||||
@@ -36,7 +36,7 @@ import PatchTypeSelector from '../components/PatchTypeSelector';
|
||||
import ProjectBrowserPopups from '../components/ProjectBrowserPopups';
|
||||
import ProjectBrowserToolbar from '../components/ProjectBrowserToolbar';
|
||||
|
||||
import { getUtmSiteUrl } from '../../utils/siteLinks';
|
||||
import { getUtmSiteUrl } from '../../utils/urls';
|
||||
import { IconGuide } from '../../utils/components/IconGuide';
|
||||
|
||||
const PATCH_TYPE = {
|
||||
|
||||
2
packages/xod-client/src/user/actionTypes.js
Normal file
2
packages/xod-client/src/user/actionTypes.js
Normal file
@@ -0,0 +1,2 @@
|
||||
export const UPDATE_COMPILE_LIMIT = 'UPDATE_COMPILE_LIMIT';
|
||||
export default {};
|
||||
12
packages/xod-client/src/user/actions.js
Normal file
12
packages/xod-client/src/user/actions.js
Normal file
@@ -0,0 +1,12 @@
|
||||
import { getCompileLimitUrl } from '../utils/urls';
|
||||
import { UPDATE_COMPILE_LIMIT } from './actionTypes';
|
||||
|
||||
export const updateCompileLimit = () => dispatch =>
|
||||
fetch(getCompileLimitUrl())
|
||||
.then(res => (res.ok ? res.json() : null))
|
||||
.catch(() => null)
|
||||
.then(limit => dispatch({
|
||||
type: UPDATE_COMPILE_LIMIT,
|
||||
payload: limit,
|
||||
}));
|
||||
export default {};
|
||||
14
packages/xod-client/src/user/reducer.js
Normal file
14
packages/xod-client/src/user/reducer.js
Normal file
@@ -0,0 +1,14 @@
|
||||
import { UPDATE_COMPILE_LIMIT } from './actionTypes';
|
||||
|
||||
const userReducer = (state = {}, action) => {
|
||||
switch (action.type) {
|
||||
case UPDATE_COMPILE_LIMIT: {
|
||||
const limit = action.payload;
|
||||
return { ...state, limit };
|
||||
}
|
||||
default:
|
||||
return state;
|
||||
}
|
||||
};
|
||||
|
||||
export default userReducer;
|
||||
14
packages/xod-client/src/user/selectors.js
Normal file
14
packages/xod-client/src/user/selectors.js
Normal file
@@ -0,0 +1,14 @@
|
||||
import R from 'ramda';
|
||||
import { createSelector } from 'reselect';
|
||||
|
||||
export const getUserState = R.prop('user');
|
||||
|
||||
export const getCompileLimit = createSelector(
|
||||
getUserState,
|
||||
R.prop('limit')
|
||||
);
|
||||
|
||||
export const getCompileLimitLeft = createSelector(
|
||||
getCompileLimit,
|
||||
limit => (limit ? limit.limit - limit.pending - limit.used : null)
|
||||
);
|
||||
3
packages/xod-client/src/user/state.js
Normal file
3
packages/xod-client/src/user/state.js
Normal file
@@ -0,0 +1,3 @@
|
||||
export default {
|
||||
limit: null,
|
||||
};
|
||||
@@ -29,3 +29,9 @@ export const getUtmSiteUrl = getUtmUrl(process.env.XOD_SITE_DOMAIN);
|
||||
*/
|
||||
// :: String -> String
|
||||
export const getUtmForumUrl = getUtmUrl(process.env.XOD_FORUM_DOMAIN, '', 'forum');
|
||||
|
||||
const HOSTNAME = process.env.XOD_HOSTNAME || 'xod.io';
|
||||
|
||||
// :: String -> String
|
||||
export const getCompileLimitUrl = () =>
|
||||
`https://compile.${HOSTNAME}/limits`;
|
||||
@@ -5778,7 +5778,7 @@ isobject@^3.0.0, isobject@^3.0.1:
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/isobject/-/isobject-3.0.1.tgz#4e431e92b11a9731636aa1f9c8d1ccbcfdab78df"
|
||||
|
||||
isomorphic-fetch@2.2.1, isomorphic-fetch@^2.1.1:
|
||||
isomorphic-fetch@2.2.1, isomorphic-fetch@^2.1.1, isomorphic-fetch@^2.2.1:
|
||||
version "2.2.1"
|
||||
resolved "https://registry.yarnpkg.com/isomorphic-fetch/-/isomorphic-fetch-2.2.1.tgz#611ae1acf14f5e81f729507472819fe9733558a9"
|
||||
dependencies:
|
||||
|
||||
Reference in New Issue
Block a user