コード例 #1
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const activateKernelEpic = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.ACTIVATE_KERNEL),
    mergeMap(({ payload: { serverId, kernelName } }) => {
      const configPath = [
        "entities",
        "serversById",
        serverId,
        "server",
        "config"
      ];
      const config = objectPath.get(store.getState(), configPath);
      return kernels.start(config, kernelName, "").pipe(
        mergeMap(data => {
          const session = uuid();
          const kernel = Object.assign({}, data.response, {
            channel: kernels.connect(config, data.response.id, session)
          });

          kernel.channel.next(kernelInfoRequest());

          return merge(
            of(
              actions.activateKernelFulfilled({
                serverId,
                kernelName,
                kernel
              })
            )
          );
        })
      );
    })
  );
コード例 #2
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const activateServerEpic = action$ =>
  action$.pipe(
    ofType(actionTypes.ACTIVATE_SERVER),
    switchMap(({ payload: { serverId, oldServerId, repo, gitref } }) => {
      return binder({ repo, gitref }, window.EventSource).pipe(
        mergeMap(message => {
          const actionsArray = [
            actions.addServerMessage({ serverId, message })
          ];
          if (message.phase === "ready") {
            const config = {
              endpoint: message.url.replace(/\/\s*$/, ""),
              uri: "/",
              token: message.token,
              crossDomain: true
            };
            actionsArray.push(
              actions.activateServerFulfilled({ serverId, config })
            );
            actionsArray.push(actions.fetchKernelSpecs({ serverId }));
            if (oldServerId) {
              // TODO: kill server epic doesn't exist yet to handle this.
              // TODO: the server will be culled once we do a jupyter shutdown call
              actionsArray.push(actions.killServer({ serverId: oldServerId }));
            }
          }
          return of(...actionsArray);
        }),
        catchError(error =>
          of(actions.activateServerFailed({ serverId, error }))
        )
      );
    })
  );
コード例 #3
0
function updateMainEpic(action$, state$, { document }) {
  return action$.pipe(
    ofType(types.updateFile, types.challengeMounted),
    filter(() => {
      const { challengeType } = challengeMetaSelector(state$.value);
      return (
        challengeType !== challengeTypes.js &&
        challengeType !== challengeTypes.bonfire
      );
    }),
    debounceTime(executeDebounceTimeout),
    switchMap(() => {
      const frameMain = createMainFramer(document, state$);
      return buildFromFiles(state$.value).pipe(
        map(frameMain),
        ignoreElements(),
        startWith(initConsole('')),
        catchError((...err) => {
          console.error(err);
          return of(disableJSOnError(err.message));
        })
      );
    }),
    catchError(err => {
      console.error(err);
      return of(disableJSOnError(err.message));
    })
  );
}
コード例 #4
0
export default function updateCompleteEpic(action$, state$) {
  return action$.pipe(
    ofType(types.updateComplete),
    filter(() => !isOnlineSelector(state$.value)),
    mapTo(onlineStatusChange(true))
  );
}
コード例 #5
0
export default function completionEpic(action$, state$) {
  return action$.pipe(
    ofType(types.submitChallenge),
    switchMap(({ type }) => {
      const state = state$.value;
      const meta = challengeMetaSelector(state);
      const { nextChallengePath, introPath, challengeType } = meta;
      const closeChallengeModal = of(closeModal('completion'));
      let submitter = () => of({ type: 'no-user-signed-in' });
      if (
        !(challengeType in submitTypes) ||
        !(submitTypes[challengeType] in submitters)
      ) {
        throw new Error(
          'Unable to find the correct submit function for challengeType ' +
            challengeType
        );
      }
      if (isSignedInSelector(state)) {
        submitter = submitters[submitTypes[challengeType]];
      }

      return submitter(type, state).pipe(
        tap(() => navigate(introPath ? introPath : nextChallengePath)),
        concat(closeChallengeModal),
        filter(Boolean)
      );
    })
  );
}
コード例 #6
0
ファイル: github-publish.js プロジェクト: jayphelps/nteract
export const publishEpic = (action$: ActionsObservable<*>, store: any) => {
  const boundHandleGistAction = handleGistAction.bind(null, store);
  return action$.pipe(
    ofType(actionTypes.PUBLISH_USER_GIST, actionTypes.PUBLISH_ANONYMOUS_GIST),
    mergeMap(action => boundHandleGistAction(action)),
    catchError(handleGistError)
  );
};
コード例 #7
0
 switchMap(() => {
   const frameReady = new Subject();
   const consoleProxy = new Subject();
   const frameTests = createTestFramer(
     document,
     state$,
     frameReady,
     consoleProxy
   );
   const challengeResults = frameReady.pipe(
     pluck('checkChallengePayload'),
     map(checkChallengePayload => ({
       checkChallengePayload,
       tests: challengeTestsSelector(state$.value)
     })),
     switchMap(({ checkChallengePayload, tests }) => {
       const postTests = of(
         updateConsole('// tests completed'),
         logsToConsole('// console output'),
         checkChallenge(checkChallengePayload)
       ).pipe(delay(250));
       return runTestsInTestFrame(document, tests).pipe(
         switchMap(tests => {
           return from(tests).pipe(
             map(({ message }) => message),
             filter(overEvery(isString, Boolean)),
             map(updateConsole),
             concat(of(updateTests(tests)))
           );
         }),
         concat(postTests)
       );
     })
   );
   const buildAndFrameChallenge = action$.pipe(
     ofType(types.executeChallenge),
     debounceTime(executeDebounceTimeout),
     filter(() => isJSEnabledSelector(state$.value)),
     switchMap(() => {
       const state = state$.value;
       const { challengeType } = challengeMetaSelector(state);
       const build =
         challengeType === backend ? buildBackendChallenge : buildFromFiles;
       return build(state).pipe(
         tap(frameTests),
         ignoreElements(),
         startWith(initLogs()),
         startWith(initConsole('// running tests')),
         catchError(err => {
           console.error(err);
           return of(disableJSOnError(err));
         })
       );
     })
   );
   const proxyConsole = consoleProxy.pipe(map(updateLogs));
   return merge(buildAndFrameChallenge, challengeResults, proxyConsole);
 })
コード例 #8
0
ファイル: config.js プロジェクト: jayphelps/nteract
export const loadConfigEpic = (action$: ActionsObservable<*>) =>
  action$.pipe(
    ofType(actionTypes.LOAD_CONFIG),
    switchMap(() =>
      readFileObservable(CONFIG_FILE_PATH).pipe(
        map(data => actions.configLoaded(JSON.parse(data)))
      )
    )
  );
コード例 #9
0
ファイル: execute.js プロジェクト: jdetle/nteract
export function createExecuteCellStream(
  action$: ActionsObservable<*>,
  store: any,
  message: ExecuteRequest,
  id: string
) {
  const state = store.getState();

  const kernel = state.app.kernel;
  const channels = kernel ? kernel.channels : null;

  const kernelConnected =
    kernel &&
    channels &&
    !(kernel.status === "starting" || kernel.status === "not connected");

  if (!kernelConnected) {
    return of({
      type: ERROR_EXECUTING,
      payload: "Kernel not connected!",
      error: true
    });
  }

  const cellStream = executeCellStream(channels, id, message).pipe(
    takeUntil(
      merge(
        action$.pipe(
          filter(laterAction => laterAction.id === id),
          ofType(ABORT_EXECUTION, REMOVE_CELL)
        ),
        action$.pipe(ofType(LAUNCH_KERNEL, LAUNCH_KERNEL_BY_NAME, KILL_KERNEL))
      )
    )
  );

  return merge(
    // We make sure to propagate back to "ourselves" the actual message
    // that we sent to the kernel with the sendExecuteMessage action
    of(sendExecuteMessage(id, message)),
    // Merging it in with the actual stream
    cellStream
  );
}
コード例 #10
0
ファイル: config.js プロジェクト: jayphelps/nteract
export const saveConfigEpic = (action$: ActionsObservable<*>, store: any) =>
  action$.pipe(
    ofType(actionTypes.SAVE_CONFIG),
    mergeMap(() =>
      writeFileObservable(
        CONFIG_FILE_PATH,
        JSON.stringify(selectors.userPreferences(store.getState()))
      ).pipe(map(actions.doneSavingConfig))
    )
  );
コード例 #11
0
export const watchExecutionStateEpic = (action$: ActionsObservable<*>) =>
  action$.pipe(
    ofType(LAUNCH_KERNEL_SUCCESSFUL),
    switchMap((action: NewKernelAction) =>
      action.kernel.channels.pipe(
        filter(msg => msg.header.msg_type === "status"),
        map(msg => setExecutionState(msg.content.execution_state))
      )
    )
  );
コード例 #12
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const initializeKernelMessaging = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.ACTIVATE_KERNEL_FULFILLED),
    // When new kernels come in we should drop our old message handling
    switchMap(({ payload }) => {
      const { kernel, kernelName, serverId } = payload;
      // Side effect! Get that Kernel Info!
      kernel.channel.next(kernelInfoRequest());
      return kernel.channel.pipe(
        mergeMap(message => {
          const actionsArray = [
            actions.addKernelMessage({ serverId, kernelName, message })
          ];
          switch (message.header.msg_type) {
            case "status":
              actionsArray.push(
                actions.setKernelStatus({
                  serverId,
                  kernelName,
                  status: message.content.execution_state
                })
              );
              break;
            case "kernel_info_reply":
              actionsArray.push(
                actions.setActiveKernelLanguageInfo({
                  serverId,
                  kernelName,
                  languageInfo: message.content.language_info
                })
              );
              break;
            case "display_data":
            case "execute_result":
            case "stream":
            case "error":
              actionsArray.push(
                actions.addKernelOutput({
                  serverId,
                  kernelName,
                  output: {
                    ...message.content,
                    output_type: message.header.msg_type
                  }
                })
              );
              break;
            default:
              break;
          }
          return from(actionsArray);
        })
      );
    })
  );
コード例 #13
0
ファイル: execute.js プロジェクト: jdetle/nteract
export function executeCellEpic(action$: ActionsObservable<*>, store: any) {
  return action$.pipe(
    ofType(EXECUTE_CELL, EXECUTE_FOCUSED_CELL),
    mergeMap(action => {
      if (action.type === EXECUTE_FOCUSED_CELL) {
        const state = store.getState();
        const id = state.document.get("cellFocused");
        if (!id) {
          throw new Error("attempted to execute without an id");
        }
        return of(executeCell(id));
      }
      return of(action);
    }),
    tap(action => {
      if (!action.id) {
        throw new Error("execute cell needs an id");
      }
    }),
    // Split stream by cell IDs
    groupBy(action => action.id),
    // Work on each cell's stream
    map(cellActionStream =>
      cellActionStream.pipe(
        // When a new EXECUTE_CELL comes in with the current ID, we create a
        // a new stream and unsubscribe from the old one.
        switchMap(({ id }) => {
          const state = store.getState();

          const cell = state.document.getIn(
            ["notebook", "cellMap", id],
            Immutable.Map()
          );

          // We only execute code cells
          if (cell.get("cell_type") !== "code") {
            return empty();
          }

          const source = cell.get("source", "");

          const message = createExecuteRequest(source);

          return createExecuteCellStream(action$, store, message, id);
        })
      )
    ),
    // Bring back all the inner Observables into one stream
    mergeAll(),
    catchError((err, source) =>
      merge(of({ type: ERROR_EXECUTING, payload: err, error: true }), source)
    )
  );
}
コード例 #14
0
ファイル: contents.js プロジェクト: jayphelps/nteract
export function fetchContentEpic(
  action$: ActionsObservable<*>,
  store: Store<*, *>
) {
  return action$.pipe(
    ofType(actionTypes.FETCH_CONTENT),
    switchMap((action: actionTypes.FetchContent) => {
      if (!action.payload || typeof action.payload.filepath !== "string") {
        return of({
          type: "ERROR",
          error: true,
          payload: { error: new Error("fetching content needs a payload") }
        });
      }

      const state = store.getState();

      const host = selectors.currentHost(state);
      if (host.type !== "jupyter") {
        // Dismiss any usage that isn't targeting a jupyter server
        return empty();
      }
      const serverConfig = selectors.serverConfig(host);

      return contents
        .get(serverConfig, action.payload.filepath, action.payload.params)
        .pipe(
          tap(xhr => {
            if (xhr.status !== 200) {
              throw new Error(xhr.response);
            }
          }),
          map(xhr => {
            return actions.fetchContentFulfilled({
              filepath: action.payload.filepath,
              model: xhr.response,
              kernelRef: action.payload.kernelRef,
              contentRef: action.payload.contentRef
            });
          }),
          catchError((xhrError: any) =>
            of(
              actions.fetchContentFailed({
                filepath: action.payload.filepath,
                error: xhrError,
                kernelRef: action.payload.kernelRef,
                contentRef: action.payload.contentRef
              })
            )
          )
        );
    })
  );
}
コード例 #15
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const extractCodeMirrorModeEpic = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.SET_ACTIVE_KERNEL_LANGUAGE_INFO),
    switchMap(({ payload }) => {
      const { languageInfo } = payload;
      return of(
        actions.setCodeMirrorMode(
          languageInfo.codemirror_mode || languageInfo.name || ""
        )
      );
    })
  );
コード例 #16
0
const loginEpic = action$ =>
  action$.pipe(
    ofType("LOGIN_REQUEST"),
    mergeMap(({ user, password }) =>
      from(Api.authorize(user, password)).pipe(
        tap(token => Api.storeItem({ token })),
        map(token => ({ type: "LOGIN_SUCCESS", token }))
      )
    ),
    catchError(error =>
      of({ type: "LOGIN_ERROR", error }).pipe(tap(_ => Api.clearItem("token")))
    )
  );
コード例 #17
0
export const launchKernelWhenNotebookSetEpic = (
  action$: ActionsObservable<*>
) =>
  action$.pipe(
    ofType(SET_NOTEBOOK),
    map((action: SetNotebookAction) => {
      const { cwd, kernelSpecName } = extractNewKernel(
        action.filename,
        action.notebook
      );

      return launchKernelByName(kernelSpecName, cwd);
    })
  );
コード例 #18
0
ファイル: execute.js プロジェクト: jdetle/nteract
export const updateDisplayEpic = (action$: ActionsObservable<*>) =>
  // Global message watcher so we need to set up a feed for each new kernel
  action$.pipe(
    ofType(LAUNCH_KERNEL_SUCCESSFUL),
    switchMap((action: NewKernelAction) =>
      action.kernel.channels.pipe(
        ofMessageType("update_display_data"),
        map(msg => updateDisplay(msg.content)),
        catchError(err =>
          of({ type: ERROR_UPDATE_DISPLAY, payload: err, error: true })
        )
      )
    )
  );
コード例 #19
0
ファイル: loading.js プロジェクト: dalejung/nteract
export const newNotebookEpic = (action$: ActionsObservable<*>) =>
  action$.pipe(
    ofType(actionTypes.NEW_NOTEBOOK),
    map((action: actionTypes.NewNotebook) => {
      const {
        payload: {
          kernelSpec: { name, spec },
          kernelRef
        }
      } = action;

      // TODO: work on a raw javascript object since we convert it over again
      let notebook = monocellNotebook;
      if (name) {
        notebook = notebook
          .setIn(["metadata", "kernel_info", "name"], name)
          .setIn(["metadata", "language_info", "name"], name);
      }
      if (spec) {
        notebook = notebook
          .setIn(["metadata", "kernelspec"], spec)
          .setIn(["metadata", "kernelspec", "name"], name);
      }

      const timestamp = new Date();

      return actions.fetchContentFulfilled({
        // NOTE: A new notebook on desktop does not have a filepath, unlike
        //       the web app which uses UntitledX.ipynb
        filepath: "",
        model: {
          type: "notebook",
          mimetype: null,
          format: "json",
          // Back to JS, only to immutableify it inside of the reducer
          content: toJS(notebook),
          writable: true,
          name: null,
          // Since we have the filepath above, do we need it here (?)
          path: null,
          created: timestamp,
          last_modified: timestamp
        },
        kernelRef: action.payload.kernelRef,
        contentRef: action.payload.contentRef
      });
    })
  );
コード例 #20
0
ファイル: kernelspecs.js プロジェクト: jayphelps/nteract
export const fetchKernelspecsEpic = (
  action$: ActionsObservable<*>,
  store: any
) =>
  action$.pipe(
    ofType(actionTypes.FETCH_KERNELSPECS),
    mergeMap((action: FetchKernelspecs) => {
      const { payload: { hostRef, kernelspecsRef } } = action;
      const state = store.getState();

      const host = selectors.currentHost(state);
      if (host.type !== "jupyter") {
        // Dismiss any usage that isn't targeting a jupyter server
        return empty();
      }
      const serverConfig = selectors.serverConfig(host);

      return kernelspecs.list(serverConfig).pipe(
        map(data => {
          const defaultKernelName = data.response.default;
          const kernelspecs = {};
          Object.keys(data.response.kernelspecs).forEach(key => {
            const value = data.response.kernelspecs[key];
            kernelspecs[key] = {
              name: value.name,
              resources: value.resources,
              argv: value.spec.argv,
              displayName: value.spec.display_name,
              env: value.spec.env,
              interruptMode: value.spec.interrupt_mode,
              language: value.spec.language,
              metadata: value.spec.metadata
            };
          });
          return actions.fetchKernelspecsFulfilled({
            hostRef,
            kernelspecsRef,
            defaultKernelName,
            kernelspecs
          });
        }),
        catchError(error => {
          return actions.fetchKernelspecsFailed({ kernelspecsRef, error });
        })
      );
    })
  );
コード例 #21
0
export const interruptKernelEpic = (
  action$: *,
  state$: StateObservable<AppState>
): Observable<redux$Action> =>
  action$.pipe(
    ofType(actions.INTERRUPT_KERNEL),
    // This epic can only interrupt direct zeromq connected kernels
    filter(() => selectors.isCurrentKernelZeroMQ(state$.value)),
    // If the user fires off _more_ interrupts, we shouldn't interrupt the in-flight
    // interrupt, instead doing it after the last one happens
    concatMap((action: actions.InterruptKernel) => {
      const kernel = selectors.currentKernel(state$.value);
      if (!kernel) {
        return of(
          actions.interruptKernelFailed({
            error: new Error("Can't interrupt a kernel we don't have"),
            kernelRef: action.payload.kernelRef
          })
        );
      }

      if (kernel.type !== "zeromq" || !kernel.spawn) {
        return of(
          actions.interruptKernelFailed({
            error: new Error("Invalid kernel type for interrupting"),
            kernelRef: action.payload.kernelRef
          })
        );
      }

      const spawn = kernel.spawn;

      //
      // From the node.js docs
      //
      // > The ChildProcess object may emit an 'error' event if the signal cannot be delivered.
      //
      // This is instead handled in the watchSpawnEpic below
      spawn.kill("SIGINT");

      return of(
        actions.interruptKernelSuccessful({
          kernelRef: action.payload.kernelRef
        })
      );
    })
  );
コード例 #22
0
export function watchSpawn(action$: *) {
  return action$.pipe(
    ofType(actions.LAUNCH_KERNEL_SUCCESSFUL),
    switchMap((action: actions.NewKernelAction) => {
      if (!action.payload.kernel.type === "zeromq") {
        throw new Error("kernel.type is not zeromq.");
      }
      // $FlowFixMe: spawn's type seems not to be defined.
      if (!action.payload.kernel.spawn) {
        throw new Error("kernel.spawn is not provided.");
      }
      const spawn: ChildProcess = action.payload.kernel.spawn;
      return Observable.create(observer => {
        spawn.on("error", error => {
          // We both set the state and make it easy for us to log the error
          observer.next(
            actions.setExecutionState({
              kernelStatus: "process errored",
              kernelRef: action.payload.kernelRef
            })
          );
          observer.error({ type: "ERROR", payload: error, err: true });
          observer.complete();
        });
        spawn.on("exit", () => {
          observer.next(
            actions.setExecutionState({
              kernelStatus: "process exited",
              kernelRef: action.payload.kernelRef
            })
          );
          observer.complete();
        });
        spawn.on("disconnect", () => {
          observer.next(
            actions.setExecutionState({
              kernelStatus: "process disconnected",
              kernelRef: action.payload.kernelRef
            })
          );
          observer.complete();
        });
      });
    })
  );
}
コード例 #23
0
ファイル: loading.js プロジェクト: dalejung/nteract
export const fetchContentEpic = (action$: ActionsObservable<*>) =>
  action$.pipe(
    ofType(actionTypes.FETCH_CONTENT),
    tap((action: actionTypes.FetchContent) => {
      // If there isn't a filepath, save-as it instead
      if (!action.payload.filepath) {
        throw new Error("fetch content needs a path");
      }
    }),
    // Switch map since we want the last load request to be the lead
    switchMap(action => {
      const filepath = action.payload.filepath;

      return forkJoin(
        readFileObservable(filepath),
        statObservable(filepath),
        // Project onto the Contents API response
        (content, stat) => createContentsResponse(filepath, stat, content)
      ).pipe(
        // Timeout after one minute
        timeout(60 * 1000),
        map(model =>
          actions.fetchContentFulfilled({
            filepath: model.path,
            model,
            kernelRef: action.payload.kernelRef,
            contentRef: action.payload.contentRef
          })
        ),
        catchError((err: Error) =>
          of(
            actions.fetchContentFailed({
              filepath,
              error: err,
              kernelRef: action.payload.kernelRef,
              contentRef: action.payload.contentRef
            })
          )
        )
      );
    })
  );
コード例 #24
0
 switchMap(() => {
   const proxyLogger = new Subject();
   const frameMain = createMainFramer(document, getState, proxyLogger);
   const buildAndFrameMain = actions.pipe(
     ofType(
       types.updateFile,
       types.executeChallenge,
       types.challengeMounted
     ),
     debounceTime(executeDebounceTimeout),
     switchMap(() =>
       buildFromFiles(getState(), true).pipe(
         map(frameMain),
         ignoreElements(),
         catchError(err => of(disableJSOnError(err)))
       )
     )
   );
   return merge(buildAndFrameMain, proxyLogger.map(updateConsole));
 })
コード例 #25
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const killServerEpic = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.KILL_SERVER),
    mergeMap(({ payload: { serverId } }) => {
      const oldServer = store.getState().entities.serversById[serverId];
      if (!oldServer)
        return of(
          actions.killServerFailed({
            serverId,
            error: `server with id ${serverId} does not exist in store.`
          })
        );
      const { config } = oldServer.server;
      return shutdown(config).pipe(
        mergeMap(data => {
          return of(actions.killServerFulfilled({ serverId }));
        }),
        catchError(error => of(actions.killServerFailed({ serverId, error })))
      );
    })
  );
コード例 #26
0
ファイル: epics.js プロジェクト: jayphelps/nteract
const fetchKernelSpecsEpic = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.FETCH_KERNEL_SPECS),
    mergeMap(({ payload: { serverId } }) => {
      const { config } = store.getState().entities.serversById[serverId].server;
      return kernelspecs.list(config).pipe(
        mergeMap(data => {
          const kernelName = data.response.default;
          return of(
            actions.fetchKernelSpecsFulfilled({
              serverId,
              response: data.response
            }),
            actions.setActiveKernel({ serverId, kernelName })
          );
        }),
        catchError(error =>
          of(actions.fetchKernelSpecsFailed({ serverId, error }))
        )
      );
    })
  );
コード例 #27
0
ファイル: contents.js プロジェクト: jdetle/nteract
export function loadEpic(
  action$: ActionsObservable<ALL_ACTIONS>,
  store: Store<*, *>
) {
  return action$.pipe(
    ofType("LOAD"),
    tap((action: LOAD_ACTION) => {
      // If there isn't a filename, save-as it instead
      if (!action.path) {
        throw new Error("load needs a path");
      }
    }),
    switchMap((action: LOAD_ACTION) => {
      const host = store.getState().app.host;
      // Normalizing to match rx-jupyter vs. host record
      const serverConfig = {
        endpoint: host.serverUrl,
        token: host.token,
        crossDomain: false
      };

      // TODO: make params optional in rx-jupyter
      return contents.get(serverConfig, action.path, {}).pipe(
        tap(xhr => {
          if (xhr.status !== 200) {
            throw new Error(xhr.response);
          }
        }),
        map(xhr => {
          return {
            type: "LOADED",
            payload: xhr.response
          };
        }),
        catchError((xhrError: any) => of(loadFailed(xhrError)))
      );
    })
  );
}
コード例 #28
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const setActiveKernelEpic = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.SET_ACTIVE_KERNEL),
    mergeMap(({ payload: { serverId, kernelName } }) => {
      const channelPath = [
        "entities",
        "serversById",
        serverId,
        "server",
        "activeKernelsByName",
        kernelName,
        "kernel",
        "channel"
      ];
      const channel = objectPath.get(store.getState(), channelPath);
      const actionsArray = [actions.setCurrentKernelName(kernelName)];
      if (!channel) {
        actionsArray.push(actions.activateKernel({ serverId, kernelName }));
      }
      return of(...actionsArray);
    })
  );
コード例 #29
0
export const launchKernelByNameEpic = (
  action$: ActionsObservable<redux$Action>
): Observable<redux$Action> =>
  action$.pipe(
    ofType(actions.LAUNCH_KERNEL_BY_NAME),
    tap((action: actions.LaunchKernelByNameAction) => {
      if (!action.payload.kernelSpecName) {
        throw new Error("launchKernelByNameEpic requires a kernel name");
      }
    }),
    mergeMap((action: actions.LaunchKernelByNameAction) =>
      kernelSpecsObservable.pipe(
        map(specs => {
          const kernelSpec = specs[action.payload.kernelSpecName];
          if (kernelSpec) {
            // Defer to a launchKernel action to _actually_ launch
            return actions.launchKernel({
              kernelSpec,
              cwd: action.payload.cwd,
              kernelRef: action.payload.kernelRef,
              selectNextKernel: action.payload.selectNextKernel,
              contentRef: action.payload.contentRef
            });
          } else {
            return actions.launchKernelFailed({
              error: new Error(
                `Kernel named ${
                  action.payload.kernelSpecName
                } does not appear to be available.`
              ),
              kernelRef: action.payload.kernelRef,
              contentRef: action.payload.contentRef
            });
          }
        })
      )
    )
  );
コード例 #30
0
ファイル: epics.js プロジェクト: captainsafia/nteract
const runSourceEpic = (action$, store) =>
  action$.pipe(
    ofType(actionTypes.RUN_SOURCE),
    mergeMap(({ payload: { serverId, kernelName, source } }) => {
      const channelPath = [
        "entities",
        "serversById",
        serverId,
        "server",
        "activeKernelsByName",
        kernelName,
        "kernel",
        "channel"
      ];
      const channel = objectPath.get(store.getState(), channelPath);
      if (channel) {
        channel.next(executeRequest(source));
      }
      return of(
        actions.clearKernelOutputs({ serverId, kernelName }),
        actions.setSource(source)
      );
    })
  );