@fc3/mmcadi 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +673 -0
- package/README.md +5 -0
- package/bin/compile +63 -0
- package/bin/copy-static-files +13 -0
- package/bin/install +5 -0
- package/bin/precompile +55 -0
- package/bin/prepublish +7 -0
- package/bin/remap-paths +113 -0
- package/bin/test +9 -0
- package/config/tsconfig.json +37 -0
- package/package.json +33 -0
- package/src/bootstrap/start.ts +12 -0
- package/src/client/bootstrap.ts +5 -0
- package/src/client/client.ts +54 -0
- package/src/client/enum/key-code.ts +34 -0
- package/src/client/enum/page-type.ts +19 -0
- package/src/client/factory/page.ts +61 -0
- package/src/client/page/confirm-delete-block.ts +30 -0
- package/src/client/page/create-block.ts +6 -0
- package/src/client/page/day.ts +8 -0
- package/src/client/page/edit-block.ts +43 -0
- package/src/client/page/edit-custom.ts +16 -0
- package/src/client/page/home.ts +8 -0
- package/src/client/page/login.ts +8 -0
- package/src/client/page/logout.ts +8 -0
- package/src/client/page/month.ts +8 -0
- package/src/client/page/move-block.ts +8 -0
- package/src/client/page/select-block-type.ts +56 -0
- package/src/client/page/settings.ts +8 -0
- package/src/client/page/view-custom.ts +665 -0
- package/src/client/page/week.ts +8 -0
- package/src/client/page/year.ts +8 -0
- package/src/client/page.ts +128 -0
- package/src/client/shim/execute.ts +5 -0
- package/src/client/shim/logger.ts +44 -0
- package/src/client/utility/get-meta-value.ts +23 -0
- package/src/common/builder/block/background.ts +25 -0
- package/src/common/builder/block/folder.ts +43 -0
- package/src/common/builder/block/header.ts +15 -0
- package/src/common/builder/block/link.ts +32 -0
- package/src/common/builder/block/multicolumn.ts +16 -0
- package/src/common/builder/block/note.ts +13 -0
- package/src/common/builder/block/whitespace.ts +13 -0
- package/src/common/utility/get-parent-path.ts +29 -0
- package/src/constant/month-names.ts +16 -0
- package/src/enum/action-type.ts +11 -0
- package/src/enum/block-type.ts +18 -0
- package/src/enum/calendar-view-mode.ts +9 -0
- package/src/enum/color.ts +15 -0
- package/src/enum/default-role.ts +6 -0
- package/src/enum/directory-item-type.ts +6 -0
- package/src/enum/emoji.ts +94 -0
- package/src/enum/field-type.ts +8 -0
- package/src/enum/header-size.ts +7 -0
- package/src/enum/permission-type.ts +8 -0
- package/src/enum/time-place-visibility.ts +8 -0
- package/src/enum/tool-type.ts +14 -0
- package/src/index.ts +8 -0
- package/src/interface/hydration-callback.ts +7 -0
- package/src/interface/provider.ts +8 -0
- package/src/interface/repository.ts +12 -0
- package/src/lib/array/add.ts +10 -0
- package/src/lib/array/assert-is-empty.ts +23 -0
- package/src/lib/array/clone.ts +5 -0
- package/src/lib/array/difference.ts +8 -0
- package/src/lib/array/empty.ts +6 -0
- package/src/lib/array/equal.ts +24 -0
- package/src/lib/array/get-first-value.ts +5 -0
- package/src/lib/array/get-last-value.ts +5 -0
- package/src/lib/array/get-max-value.ts +5 -0
- package/src/lib/array/get-value-after.ts +23 -0
- package/src/lib/array/get-value-before.ts +23 -0
- package/src/lib/array/get-values-between.ts +18 -0
- package/src/lib/array/index.ts +5 -0
- package/src/lib/array/is-empty.ts +6 -0
- package/src/lib/array/remove.ts +19 -0
- package/src/lib/array/sum.ts +11 -0
- package/src/lib/array/unique.ts +13 -0
- package/src/lib/environment/bootstrap.ts +1 -0
- package/src/lib/environment/enum/environment-type.ts +8 -0
- package/src/lib/environment/enum/service-type.ts +5 -0
- package/src/lib/environment/index.ts +7 -0
- package/src/lib/environment/utility/get-environment-type.ts +28 -0
- package/src/lib/environment/utility/is-browser.ts +5 -0
- package/src/lib/environment/utility/is-development.ts +10 -0
- package/src/lib/environment/utility/is-production-or-staging.ts +8 -0
- package/src/lib/environment/utility/is-production.ts +10 -0
- package/src/lib/environment/utility/is-staging.ts +10 -0
- package/src/lib/errors/enum/error-type.ts +13 -0
- package/src/lib/errors/error/base.ts +40 -0
- package/src/lib/errors/error/conflict.ts +16 -0
- package/src/lib/errors/error/generic.ts +23 -0
- package/src/lib/errors/error/invalid.ts +14 -0
- package/src/lib/errors/error/invariant-violation.ts +5 -0
- package/src/lib/errors/error/not-allowed.ts +14 -0
- package/src/lib/errors/error/not-found.ts +16 -0
- package/src/lib/errors/error/not-implemented.ts +20 -0
- package/src/lib/errors/error/omitted.ts +14 -0
- package/src/lib/errors/error/timeout.ts +14 -0
- package/src/lib/errors/error/unauthorized.ts +14 -0
- package/src/lib/errors/index.ts +18 -0
- package/src/lib/errors/sugar/invariant.ts +7 -0
- package/src/lib/errors/type/coded-error.ts +7 -0
- package/src/lib/errors/type/error-data.ts +11 -0
- package/src/lib/errors/utility/create-error-for-error-type.ts +60 -0
- package/src/lib/errors/utility/create-error-from-ambiguous-json-data.ts +26 -0
- package/src/lib/errors/utility/error-matches.ts +28 -0
- package/src/lib/errors/utility/get-error-type-for-posix-error-code.ts +37 -0
- package/src/lib/errors/utility/get-error-type-for-status-code.ts +38 -0
- package/src/lib/errors/utility/get-message-for-error-type.ts +29 -0
- package/src/lib/errors/utility/matches-posix-error-code.ts +11 -0
- package/src/lib/errors/utility/wrap-error.ts +39 -0
- package/src/lib/event-emitter/index.ts +63 -0
- package/src/lib/execution-context/execution-context.ts +90 -0
- package/src/lib/execution-context/index.ts +8 -0
- package/src/lib/execution-context/type/session.ts +7 -0
- package/src/lib/feature/feature.ts +108 -0
- package/src/lib/feature/index.ts +3 -0
- package/src/lib/filesystem/bootstrap.ts +1 -0
- package/src/lib/filesystem/enum/file-extension.ts +19 -0
- package/src/lib/filesystem/index.ts +4 -0
- package/src/lib/filesystem/utility/exists.ts +21 -0
- package/src/lib/filesystem/utility/get-extension-for-filepath.ts +20 -0
- package/src/lib/filesystem/utility/strip-extension.ts +26 -0
- package/src/lib/grammar/index.ts +3 -0
- package/src/lib/grammar/noun-inflector.ts +104 -0
- package/src/lib/grammar/utility/get-words-from-identifier.ts +9 -0
- package/src/lib/grammar/verb-inflector.ts +344 -0
- package/src/lib/http/buffer-stream.ts +76 -0
- package/src/lib/http/enum/content-type.ts +19 -0
- package/src/lib/http/enum/cookie-attribute.ts +11 -0
- package/src/lib/http/enum/header.ts +29 -0
- package/src/lib/http/enum/method.ts +11 -0
- package/src/lib/http/enum/same-site-policy.ts +7 -0
- package/src/lib/http/enum/status-code.ts +9 -0
- package/src/lib/http/factory/body-parser.ts +55 -0
- package/src/lib/http/index.ts +24 -0
- package/src/lib/http/interface/client-request.ts +15 -0
- package/src/lib/http/interface/incoming-message.ts +24 -0
- package/src/lib/http/interface/network-library.ts +9 -0
- package/src/lib/http/interface/request-callback.ts +7 -0
- package/src/lib/http/isomorphic/request.ts +77 -0
- package/src/lib/http/isomorphic/response.ts +77 -0
- package/src/lib/http/isomorphic.ts +20 -0
- package/src/lib/http/parser/accept-header.ts +35 -0
- package/src/lib/http/parser/basic-auth-header.ts +48 -0
- package/src/lib/http/parser/body/json.ts +14 -0
- package/src/lib/http/parser/body/multipart.ts +89 -0
- package/src/lib/http/parser/body/url-encoded.ts +16 -0
- package/src/lib/http/parser/body.ts +44 -0
- package/src/lib/http/parser/cookie.ts +114 -0
- package/src/lib/http/parser/querystring.ts +92 -0
- package/src/lib/http/parser/url.ts +76 -0
- package/src/lib/http/request/incoming.ts +299 -0
- package/src/lib/http/request/outgoing.ts +276 -0
- package/src/lib/http/request.ts +26 -0
- package/src/lib/http/response/incoming.ts +243 -0
- package/src/lib/http/response/outgoing.ts +160 -0
- package/src/lib/http/response.ts +74 -0
- package/src/lib/http/serializer/basic-auth-header.ts +27 -0
- package/src/lib/http/serializer/cookie.ts +90 -0
- package/src/lib/http/serializer/query-data.ts +54 -0
- package/src/lib/http/transaction.ts +320 -0
- package/src/lib/http/type/basic-auth-credentials.ts +6 -0
- package/src/lib/http/type/header-map.ts +5 -0
- package/src/lib/http/type/log-attributes.ts +12 -0
- package/src/lib/http/type/path-parameters.ts +5 -0
- package/src/lib/http/type/query-data.ts +7 -0
- package/src/lib/http/type/query-value.ts +11 -0
- package/src/lib/http/type/request-options.ts +16 -0
- package/src/lib/http/type/transaction-data.ts +4 -0
- package/src/lib/http/utility/get-content-type-for-extension.ts +47 -0
- package/src/lib/http/utility/get-library-for-protocol.ts +25 -0
- package/src/lib/http/utility/get-status-code-for-error-type.ts +37 -0
- package/src/lib/http/utility/get-status-code-for-error.ts +13 -0
- package/src/lib/http/utility/is-client-error-status.ts +15 -0
- package/src/lib/http/utility/is-error-status.ts +9 -0
- package/src/lib/http/utility/is-server-error-status.ts +7 -0
- package/src/lib/http/utility/is-success-status.ts +7 -0
- package/src/lib/http/utility/proxy-request.ts +58 -0
- package/src/lib/http/utility/serialize-request-options.ts +9 -0
- package/src/lib/http/utility/slug-generator.ts +20 -0
- package/src/lib/key-generator/index.ts +3 -0
- package/src/lib/key-generator/key-generator.ts +7 -0
- package/src/lib/logger/enum/ansi-escape-code.ts +14 -0
- package/src/lib/logger/enum/log-level.ts +8 -0
- package/src/lib/logger/formatter.ts +59 -0
- package/src/lib/logger/index.ts +7 -0
- package/src/lib/logger/interface/error-reporter.ts +7 -0
- package/src/lib/logger/interface/logger.ts +13 -0
- package/src/lib/logger/logger.ts +239 -0
- package/src/lib/logger/type/error-parameters.ts +9 -0
- package/src/lib/logger/type/loggable-data.ts +5 -0
- package/src/lib/logger/type/loggable-value.ts +1 -0
- package/src/lib/metrics/dispatcher.ts +264 -0
- package/src/lib/metrics/enum/dispatch-mode.ts +6 -0
- package/src/lib/metrics/index.ts +2 -0
- package/src/lib/metrics/settings-hydrator.ts +51 -0
- package/src/lib/metrics/type/dispatcher-settings.ts +12 -0
- package/src/lib/metrics/type/tag-map.ts +5 -0
- package/src/lib/network/bootstrap.ts +1 -0
- package/src/lib/network/enum/connection-status.ts +14 -0
- package/src/lib/network/enum/http-status-code.ts +75 -0
- package/src/lib/network/enum/network-protocol.ts +10 -0
- package/src/lib/network/event-emitter.ts +63 -0
- package/src/lib/network/index.ts +7 -0
- package/src/lib/network/interface/socket.ts +42 -0
- package/src/lib/network/type/socket-options.ts +6 -0
- package/src/lib/network/utility/get-protocol-from-url.ts +15 -0
- package/src/lib/operation/index.ts +6 -0
- package/src/lib/operation/operation/auto-logging.ts +94 -0
- package/src/lib/operation/operation/silent.ts +17 -0
- package/src/lib/operation/operation.ts +80 -0
- package/src/lib/process/bootstrap.ts +1 -0
- package/src/lib/process/enum/posix-error-code.ts +138 -0
- package/src/lib/process/enum/process-signal.ts +68 -0
- package/src/lib/process/error.ts +6 -0
- package/src/lib/process/execute.ts +77 -0
- package/src/lib/process/index.ts +4 -0
- package/src/lib/process/type/command-options.ts +9 -0
- package/src/lib/process/utility/bind-process-lifespan-to.ts +10 -0
- package/src/lib/promise-wrapper/index.ts +3 -0
- package/src/lib/promise-wrapper/promise-wrapper.ts +51 -0
- package/src/lib/random/chance.ts +5 -0
- package/src/lib/random/element.ts +7 -0
- package/src/lib/random/elements.ts +12 -0
- package/src/lib/random/enum.ts +34 -0
- package/src/lib/random/enums.ts +11 -0
- package/src/lib/random/index.ts +3 -0
- package/src/lib/random/number.ts +8 -0
- package/src/lib/server/base.ts +194 -0
- package/src/lib/server/enum/server-event.ts +5 -0
- package/src/lib/server/enum/server-status.ts +10 -0
- package/src/lib/server/http/endpoint/ping.ts +21 -0
- package/src/lib/server/http/endpoint.ts +345 -0
- package/src/lib/server/http/interface/endpoint-constructor.ts +12 -0
- package/src/lib/server/http/interface/result-serializer.ts +5 -0
- package/src/lib/server/http/middleware.ts +18 -0
- package/src/lib/server/http/result-serializer/html.ts +92 -0
- package/src/lib/server/http/result-serializer/json.ts +23 -0
- package/src/lib/server/http/route.ts +104 -0
- package/src/lib/server/http/router.ts +125 -0
- package/src/lib/server/http/type/session-resolver.ts +8 -0
- package/src/lib/server/http/utility/create-server.ts +34 -0
- package/src/lib/server/http/utility/path-parser.ts +49 -0
- package/src/lib/server/http/utility/standardize-html-indentation.ts +54 -0
- package/src/lib/server/http/websocket-wrapper.ts +83 -0
- package/src/lib/server/http.ts +301 -0
- package/src/lib/server/index.ts +5 -0
- package/src/lib/server/tcp.ts +53 -0
- package/src/lib/server/type/server-options.ts +10 -0
- package/src/lib/string/calculate-length.ts +17 -0
- package/src/lib/string/capitalize.ts +8 -0
- package/src/lib/string/create-slug.ts +14 -0
- package/src/lib/string/enum/ansi-escape-code.ts +14 -0
- package/src/lib/string/enum/string-encoding.ts +9 -0
- package/src/lib/string/hyphenate.ts +5 -0
- package/src/lib/string/index.ts +3 -0
- package/src/lib/string/pad.ts +14 -0
- package/src/lib/string/trim-multiline.ts +21 -0
- package/src/lib/string/trim.ts +8 -0
- package/src/lib/tcp/channel.ts +13 -0
- package/src/lib/tcp/connection/incoming.ts +72 -0
- package/src/lib/tcp/connection/outgoing.ts +219 -0
- package/src/lib/tcp/connection.ts +360 -0
- package/src/lib/tcp/enum/connection-event.ts +12 -0
- package/src/lib/tcp/enum/message-type.ts +9 -0
- package/src/lib/tcp/index.ts +1 -0
- package/src/lib/tcp/type/connection-parameters.ts +6 -0
- package/src/lib/tcp/type/message/channel-close.ts +9 -0
- package/src/lib/tcp/type/message/channel-open.ts +9 -0
- package/src/lib/tcp/type/message.ts +10 -0
- package/src/lib/test/index.ts +2 -0
- package/src/lib/test/utility/build-config.ts +17 -0
- package/src/lib/test/utility/build-execution-context.ts +11 -0
- package/src/lib/time/bootstrap.ts +1 -0
- package/src/lib/time/enum/time-interval.ts +12 -0
- package/src/lib/time/index.ts +4 -0
- package/src/lib/time/utility/format-duration.ts +139 -0
- package/src/lib/time/utility/format-relative-duration.ts +22 -0
- package/src/lib/time/utility/sleep.ts +9 -0
- package/src/operation.ts +18 -0
- package/src/server/endpoint/abstract-page.ts +126 -0
- package/src/server/endpoint/action/create.ts +545 -0
- package/src/server/endpoint/action/get.ts +231 -0
- package/src/server/endpoint/base.ts +51 -0
- package/src/server/endpoint/day.ts +13 -0
- package/src/server/endpoint/generic-page.ts +14 -0
- package/src/server/endpoint/index.ts +11 -0
- package/src/server/endpoint/login.ts +45 -0
- package/src/server/endpoint/logout.ts +38 -0
- package/src/server/endpoint/month.ts +35 -0
- package/src/server/endpoint/robots.ts +18 -0
- package/src/server/endpoint/session/create.ts +62 -0
- package/src/server/endpoint/settings/get.ts +40 -0
- package/src/server/endpoint/settings/update.ts +44 -0
- package/src/server/endpoint/today.ts +15 -0
- package/src/server/endpoint/week.ts +34 -0
- package/src/server/endpoint/year.ts +34 -0
- package/src/server/enum/custom-page-type.ts +10 -0
- package/src/server/factory/block-result-serializer.ts +115 -0
- package/src/server/middleware/base.ts +6 -0
- package/src/server/middleware/error-handler.ts +177 -0
- package/src/server/middleware/static-file.ts +83 -0
- package/src/server/operation/add-block.ts +110 -0
- package/src/server/operation/create-session.ts +43 -0
- package/src/server/operation/delete-block.ts +96 -0
- package/src/server/operation/demote-block.ts +108 -0
- package/src/server/operation/destroy-session.ts +26 -0
- package/src/server/operation/load-account.ts +30 -0
- package/src/server/operation/load-block.ts +48 -0
- package/src/server/operation/load-directory-items.ts +75 -0
- package/src/server/operation/load-page.ts +368 -0
- package/src/server/operation/promote-block.ts +104 -0
- package/src/server/operation/save-page.ts +60 -0
- package/src/server/operation/update-account-settings.ts +52 -0
- package/src/server/operation/update-block.ts +124 -0
- package/src/server/repository/memory.ts +112 -0
- package/src/server/result-serializer/action.ts +939 -0
- package/src/server/result-serializer/base.ts +1267 -0
- package/src/server/result-serializer/block/audio.ts +33 -0
- package/src/server/result-serializer/block/background.ts +20 -0
- package/src/server/result-serializer/block/calendar.ts +148 -0
- package/src/server/result-serializer/block/directory.ts +57 -0
- package/src/server/result-serializer/block/ephemeral.ts +14 -0
- package/src/server/result-serializer/block/folder.ts +106 -0
- package/src/server/result-serializer/block/header.ts +31 -0
- package/src/server/result-serializer/block/image.ts +46 -0
- package/src/server/result-serializer/block/link.ts +40 -0
- package/src/server/result-serializer/block/list.ts +140 -0
- package/src/server/result-serializer/block/multi-column.ts +97 -0
- package/src/server/result-serializer/block/note.ts +44 -0
- package/src/server/result-serializer/block/todo.ts +78 -0
- package/src/server/result-serializer/block/whitespace.ts +15 -0
- package/src/server/result-serializer/block.ts +248 -0
- package/src/server/result-serializer/common/time-place-options.ts +33 -0
- package/src/server/result-serializer/login.ts +58 -0
- package/src/server/result-serializer/month.ts +170 -0
- package/src/server/result-serializer/page.ts +548 -0
- package/src/server/result-serializer/settings.ts +85 -0
- package/src/server/result-serializer/week.ts +195 -0
- package/src/server/result-serializer/year.ts +160 -0
- package/src/server/utility/accepts-content-type.ts +16 -0
- package/src/server/utility/accepts-html.ts +9 -0
- package/src/server/utility/accepts-json.ts +9 -0
- package/src/server/utility/add-days.ts +11 -0
- package/src/server/utility/create-date.ts +23 -0
- package/src/server/utility/create-index-path.ts +5 -0
- package/src/server/utility/create-slug.ts +9 -0
- package/src/server/utility/create-toast-path.ts +19 -0
- package/src/server/utility/date-less-than.ts +5 -0
- package/src/server/utility/date-occurs-before.ts +22 -0
- package/src/server/utility/date-to-key.ts +7 -0
- package/src/server/utility/date-to-label.ts +5 -0
- package/src/server/utility/date-to-path.ts +9 -0
- package/src/server/utility/dates-are-equal.ts +22 -0
- package/src/server/utility/dates-are-in-order.ts +9 -0
- package/src/server/utility/dates-are-on-the-same-day.ts +9 -0
- package/src/server/utility/dates-in-same-month.ts +8 -0
- package/src/server/utility/day-to-date.ts +40 -0
- package/src/server/utility/decrement-date.ts +11 -0
- package/src/server/utility/get-block-at-index-path.ts +32 -0
- package/src/server/utility/get-block-permissions.ts +15 -0
- package/src/server/utility/get-compact-label-for-date.ts +8 -0
- package/src/server/utility/get-custom-page-type-for-path.ts +37 -0
- package/src/server/utility/get-element-id-for-block.ts +15 -0
- package/src/server/utility/get-emoji-for-block-type.ts +39 -0
- package/src/server/utility/get-emoji-for-tool-type.ts +20 -0
- package/src/server/utility/get-end-of-month.ts +13 -0
- package/src/server/utility/get-end-of-week.ts +13 -0
- package/src/server/utility/get-filepath-for-folder-block.ts +23 -0
- package/src/server/utility/get-hex-for-color.ts +31 -0
- package/src/server/utility/get-label-for-time-place-visibility.ts +23 -0
- package/src/server/utility/get-month-name.ts +18 -0
- package/src/server/utility/get-next-day.ts +7 -0
- package/src/server/utility/get-next-month.ts +12 -0
- package/src/server/utility/get-next-week.ts +12 -0
- package/src/server/utility/get-next-year.ts +13 -0
- package/src/server/utility/get-ordinal-label-for-week.ts +11 -0
- package/src/server/utility/get-ordinal-of-week-within-month.ts +15 -0
- package/src/server/utility/get-padded-date.ts +11 -0
- package/src/server/utility/get-parent-index-path.ts +18 -0
- package/src/server/utility/get-path-for-folder-block.ts +25 -0
- package/src/server/utility/get-path-from-url.ts +13 -0
- package/src/server/utility/get-previous-index-path.ts +27 -0
- package/src/server/utility/get-previous-month.ts +12 -0
- package/src/server/utility/get-previous-week.ts +11 -0
- package/src/server/utility/get-previous-year.ts +13 -0
- package/src/server/utility/get-random-emoji-for-date.ts +109 -0
- package/src/server/utility/get-short-label-for-date.ts +11 -0
- package/src/server/utility/get-short-month-name.ts +9 -0
- package/src/server/utility/get-short-ordinal.ts +26 -0
- package/src/server/utility/get-siblings-and-index-for-index-path.ts +67 -0
- package/src/server/utility/get-start-of-month.ts +11 -0
- package/src/server/utility/get-start-of-week.ts +12 -0
- package/src/server/utility/get-start-of-year.ts +12 -0
- package/src/server/utility/get-weekday-name.ts +24 -0
- package/src/server/utility/increment-date.ts +15 -0
- package/src/server/utility/is-index-path.ts +5 -0
- package/src/server/utility/key-to-date.ts +25 -0
- package/src/server/utility/month-has-week-containing-date.ts +13 -0
- package/src/server/utility/month-to-date.ts +28 -0
- package/src/server/utility/month-to-path.ts +10 -0
- package/src/server/utility/months-are-equal.ts +8 -0
- package/src/server/utility/parse-index-path.ts +23 -0
- package/src/server/utility/path-is-date.ts +13 -0
- package/src/server/utility/path-to-date.ts +24 -0
- package/src/server/utility/subtract-days.ts +7 -0
- package/src/server/utility/validate-month.ts +10 -0
- package/src/server/utility/validate-page.ts +46 -0
- package/src/server/utility/validate-path.ts +9 -0
- package/src/server/utility/validate-url.ts +12 -0
- package/src/server/utility/week-greater-than.ts +10 -0
- package/src/server/utility/week-to-date.ts +8 -0
- package/src/server/utility/week-to-path.ts +12 -0
- package/src/server/utility/weeks-are-equal.ts +8 -0
- package/src/server/utility/year-to-date.ts +26 -0
- package/src/server/utility/year-to-path.ts +7 -0
- package/src/server/utility/years-are-equal.ts +8 -0
- package/src/server.ts +140 -0
- package/src/test.ts +195 -0
- package/src/type/account-settings.ts +9 -0
- package/src/type/account.ts +11 -0
- package/src/type/action/add-block.ts +74 -0
- package/src/type/action/complete-block.ts +10 -0
- package/src/type/action/delete-block.ts +11 -0
- package/src/type/action/demote-block.ts +9 -0
- package/src/type/action/edit-block.ts +11 -0
- package/src/type/action/promote-block.ts +9 -0
- package/src/type/action.ts +9 -0
- package/src/type/block/audio.ts +8 -0
- package/src/type/block/background.ts +10 -0
- package/src/type/block/directory.ts +18 -0
- package/src/type/block/ephemeral.ts +9 -0
- package/src/type/block/folder.ts +14 -0
- package/src/type/block/header.ts +11 -0
- package/src/type/block/image.ts +8 -0
- package/src/type/block/link.ts +12 -0
- package/src/type/block/list.ts +24 -0
- package/src/type/block/multi-column.ts +10 -0
- package/src/type/block/note.ts +9 -0
- package/src/type/block/todo.ts +10 -0
- package/src/type/block/whitespace.ts +9 -0
- package/src/type/block-metadata.ts +14 -0
- package/src/type/block.ts +18 -0
- package/src/type/day.ts +5 -0
- package/src/type/field-definition.ts +8 -0
- package/src/type/field-value.ts +5 -0
- package/src/type/file.ts +6 -0
- package/src/type/month.ts +5 -0
- package/src/type/page.ts +8 -0
- package/src/type/price.ts +11 -0
- package/src/type/resource.ts +5 -0
- package/src/type/runtime-config.ts +13 -0
- package/src/type/server-settings.ts +17 -0
- package/src/type/toast.ts +8 -0
- package/src/type/week.ts +5 -0
- package/src/type/year.ts +5 -0
- package/test/unit/index.ts +11 -0
- package/test/unit/server/operation/promote-block.ts +84 -0
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
import {ContentType, HttpMethod} from 'lib/http';
|
|
2
|
+
|
|
3
|
+
import PageResultSerializer, {PageMetadata} from 'server/result-serializer/page';
|
|
4
|
+
import BaseEndpoint from 'server/endpoint/base';
|
|
5
|
+
import BlockType from 'enum/block-type';
|
|
6
|
+
import LoadPageOperation from 'server/operation/load-page';
|
|
7
|
+
import getPathForFolderBlock from 'server/utility/get-path-for-folder-block';
|
|
8
|
+
import FolderBlock from 'type/block/folder';
|
|
9
|
+
import validateUrl from 'server/utility/validate-url';
|
|
10
|
+
import Page from 'type/page';
|
|
11
|
+
import createIndexPath from 'server/utility/create-index-path';
|
|
12
|
+
import getCustomPageTypeForPath from 'server/utility/get-custom-page-type-for-path';
|
|
13
|
+
import Toast from 'type/toast';
|
|
14
|
+
import LoadAccountOperation from 'server/operation/load-account';
|
|
15
|
+
import Color from 'enum/color';
|
|
16
|
+
|
|
17
|
+
type PageInput = {}
|
|
18
|
+
type PageOutput = Page;
|
|
19
|
+
|
|
20
|
+
abstract class AbstractPageEndpoint extends BaseEndpoint<PageInput, PageOutput> {
|
|
21
|
+
public method = HttpMethod.GET;
|
|
22
|
+
|
|
23
|
+
public content_types = [
|
|
24
|
+
ContentType.HTML,
|
|
25
|
+
ContentType.JSON
|
|
26
|
+
];
|
|
27
|
+
|
|
28
|
+
protected async process(): Promise<PageOutput> {
|
|
29
|
+
const execution_context = this.getExecutionContext();
|
|
30
|
+
const session = this.getSession();
|
|
31
|
+
|
|
32
|
+
execution_context.setSession(session);
|
|
33
|
+
|
|
34
|
+
const path = await this.determinePath();
|
|
35
|
+
const operation = new LoadPageOperation(path, execution_context);
|
|
36
|
+
|
|
37
|
+
return operation.perform();
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
protected async getHtmlResultSerializer(page: Page): Promise<PageResultSerializer> {
|
|
41
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
42
|
+
|
|
43
|
+
const target_index_path = (() => {
|
|
44
|
+
const path_parameter = this.getQueryParameter('index_path') as string;
|
|
45
|
+
|
|
46
|
+
if (path_parameter) {
|
|
47
|
+
return path_parameter;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
const referrer_url = this.getReferrerUrl();
|
|
51
|
+
|
|
52
|
+
if (referrer_url !== null) {
|
|
53
|
+
let index = 0;
|
|
54
|
+
|
|
55
|
+
while (index < page.blocks.length) {
|
|
56
|
+
const block = page.blocks[index];
|
|
57
|
+
|
|
58
|
+
if (block.block_type === BlockType.FOLDER) {
|
|
59
|
+
const folder_block = block as FolderBlock;
|
|
60
|
+
|
|
61
|
+
const block_path = getPathForFolderBlock({
|
|
62
|
+
base_path: page.path,
|
|
63
|
+
block: folder_block
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
validateUrl(referrer_url);
|
|
67
|
+
|
|
68
|
+
const url = new URL(referrer_url);
|
|
69
|
+
|
|
70
|
+
if (url.pathname === block_path) {
|
|
71
|
+
return createIndexPath([index]);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
index++;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
return null;
|
|
80
|
+
})();
|
|
81
|
+
|
|
82
|
+
const toast_message = this.getQueryParameter('toast_message') as string;
|
|
83
|
+
const custom_page_type = getCustomPageTypeForPath(page.path);
|
|
84
|
+
|
|
85
|
+
let toast: Toast | null = null;
|
|
86
|
+
|
|
87
|
+
if (toast_message) {
|
|
88
|
+
const raw_color = this.getQueryParameter('toast_color') as string;
|
|
89
|
+
const toast_color = raw_color ? decodeURIComponent(raw_color) as Color : Color.GREY;
|
|
90
|
+
|
|
91
|
+
toast = {
|
|
92
|
+
message: decodeURIComponent(toast_message),
|
|
93
|
+
color: toast_color
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
const execution_context = this.getExecutionContext();
|
|
98
|
+
const account_operation = new LoadAccountOperation(execution_context);
|
|
99
|
+
const account = await account_operation.perform();
|
|
100
|
+
const {roles} = execution_context.getConfig();
|
|
101
|
+
|
|
102
|
+
const metadata: PageMetadata = {
|
|
103
|
+
editing,
|
|
104
|
+
target_index_path,
|
|
105
|
+
toast,
|
|
106
|
+
custom_page_type,
|
|
107
|
+
roles,
|
|
108
|
+
account
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
const session = this.getSession();
|
|
112
|
+
const referrer_url = this.getReferrerUrl();
|
|
113
|
+
|
|
114
|
+
return new PageResultSerializer(
|
|
115
|
+
page,
|
|
116
|
+
metadata,
|
|
117
|
+
page.path,
|
|
118
|
+
referrer_url,
|
|
119
|
+
session
|
|
120
|
+
);
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
protected abstract determinePath(): Promise<string>;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
export default AbstractPageEndpoint;
|
|
@@ -0,0 +1,545 @@
|
|
|
1
|
+
import {unlink, copyFile, mkdir} from 'fs/promises';
|
|
2
|
+
|
|
3
|
+
import {ContentType, HttpMethod, HttpHeader, StatusCode} from 'lib/http';
|
|
4
|
+
import {InvalidError, UnauthorizedError} from 'lib/errors';
|
|
5
|
+
|
|
6
|
+
import BaseEndpoint from 'server/endpoint/base';
|
|
7
|
+
import AddBlockOperation from 'server/operation/add-block';
|
|
8
|
+
import Emoji from 'enum/emoji';
|
|
9
|
+
import DeleteBlockOperation from 'server/operation/delete-block';
|
|
10
|
+
import Color from 'enum/color';
|
|
11
|
+
import PromoteBlockOperation from 'server/operation/promote-block';
|
|
12
|
+
import PermissionType from 'enum/permission-type';
|
|
13
|
+
import getBlockAtIndexPath from 'server/utility/get-block-at-index-path';
|
|
14
|
+
import MultiColumnBlock from 'type/block/multi-column';
|
|
15
|
+
import LinkBlock from 'type/block/link';
|
|
16
|
+
import DemoteBlockOperation from 'server/operation/demote-block';
|
|
17
|
+
import UpdateBlockOperation from 'server/operation/update-block';
|
|
18
|
+
import createToastPath from 'server/utility/create-toast-path';
|
|
19
|
+
import TimePlaceVisibility from 'enum/time-place-visibility';
|
|
20
|
+
import LoadPageOperation from 'server/operation/load-page';
|
|
21
|
+
import File from 'type/file';
|
|
22
|
+
import HeaderBlock from 'type/block/header';
|
|
23
|
+
import TodoBlock from 'type/block/todo';
|
|
24
|
+
import BlockType from 'enum/block-type';
|
|
25
|
+
import AudioBlock from 'type/block/audio';
|
|
26
|
+
import BackgroundBlock from 'type/block/background';
|
|
27
|
+
import WhitespaceBlock from 'type/block/whitespace';
|
|
28
|
+
import NoteBlock from 'type/block/note';
|
|
29
|
+
import FolderBlock from 'type/block/folder';
|
|
30
|
+
import ImageBlock from 'type/block/image';
|
|
31
|
+
import Block from 'type/block';
|
|
32
|
+
import ActionType from 'enum/action-type';
|
|
33
|
+
import AddBlockAction, {
|
|
34
|
+
AddFolderBlockAction,
|
|
35
|
+
AddLinkBlockAction,
|
|
36
|
+
AddNoteBlockAction,
|
|
37
|
+
AddHeaderBlockAction,
|
|
38
|
+
AddTodoBlockAction,
|
|
39
|
+
AddMultiColumnBlockAction,
|
|
40
|
+
AddWhitespaceBlockAction,
|
|
41
|
+
AddBackgroundBlockAction
|
|
42
|
+
} from 'type/action/add-block';
|
|
43
|
+
import DeleteBlockAction from 'type/action/delete-block';
|
|
44
|
+
import CompleteBlockAction from 'type/action/complete-block';
|
|
45
|
+
import DemoteBlockAction from 'type/action/demote-block';
|
|
46
|
+
import PromoteBlockAction from 'type/action/promote-block';
|
|
47
|
+
import Action from 'type/action';
|
|
48
|
+
import getPreviousIndexPath from 'server/utility/get-previous-index-path';
|
|
49
|
+
|
|
50
|
+
type MultipartFile = {
|
|
51
|
+
readonly filepath: string;
|
|
52
|
+
readonly size: number;
|
|
53
|
+
readonly mimetype: string;
|
|
54
|
+
readonly originalFilename: string;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
type FilePayload = {
|
|
58
|
+
readonly files: MultipartFile[];
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
type ActionWithFiles = Action & FilePayload;
|
|
62
|
+
|
|
63
|
+
type CreateActionInput = Action;
|
|
64
|
+
type CreateActionOutput = string;
|
|
65
|
+
|
|
66
|
+
class CreateActionEndpoint extends BaseEndpoint<CreateActionInput, CreateActionOutput> {
|
|
67
|
+
public path = '/actions';
|
|
68
|
+
public method = HttpMethod.POST;
|
|
69
|
+
public content_types = [
|
|
70
|
+
ContentType.JSON,
|
|
71
|
+
ContentType.HTML
|
|
72
|
+
];
|
|
73
|
+
|
|
74
|
+
protected async authorize(): Promise<void> {
|
|
75
|
+
const session = this.getSession();
|
|
76
|
+
const {account_id} = session;
|
|
77
|
+
|
|
78
|
+
if (account_id === null) {
|
|
79
|
+
throw new UnauthorizedError();
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
protected async process(): Promise<CreateActionOutput> {
|
|
84
|
+
const redirect_url = await this.processBlock();
|
|
85
|
+
const response = this.getResponse();
|
|
86
|
+
|
|
87
|
+
response.setHeaderValue(HttpHeader.LOCATION, redirect_url);
|
|
88
|
+
response.setStatusCode(StatusCode.REDIRECT);
|
|
89
|
+
|
|
90
|
+
return '';
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
private async processBlock(): Promise<string> {
|
|
94
|
+
const action_type = this.getActionType();
|
|
95
|
+
|
|
96
|
+
switch (action_type) {
|
|
97
|
+
case ActionType.ADD_BLOCK:
|
|
98
|
+
return this.processAddBlock();
|
|
99
|
+
|
|
100
|
+
case ActionType.DELETE_BLOCK:
|
|
101
|
+
return this.processDeleteBlock();
|
|
102
|
+
|
|
103
|
+
case ActionType.PROMOTE_BLOCK:
|
|
104
|
+
return this.processPromoteBlock();
|
|
105
|
+
|
|
106
|
+
case ActionType.DEMOTE_BLOCK:
|
|
107
|
+
return this.processDemoteBlock();
|
|
108
|
+
|
|
109
|
+
case ActionType.EDIT_BLOCK:
|
|
110
|
+
return this.processEditBlock();
|
|
111
|
+
|
|
112
|
+
case ActionType.COMPLETE_BLOCK:
|
|
113
|
+
return this.processCompleteBlock();
|
|
114
|
+
|
|
115
|
+
default:
|
|
116
|
+
throw new InvalidError(`Unsupported action type: ${action_type}`);
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
private async processAddBlock(): Promise<string> {
|
|
121
|
+
const filenames = await this.storeFiles();
|
|
122
|
+
const body = this.getRequestBody() as AddBlockAction;
|
|
123
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
124
|
+
|
|
125
|
+
const action: AddBlockAction = {
|
|
126
|
+
...body,
|
|
127
|
+
editing
|
|
128
|
+
};
|
|
129
|
+
|
|
130
|
+
const {index_path} = action;
|
|
131
|
+
|
|
132
|
+
const files = filenames.map((filename) => {
|
|
133
|
+
const description = null;
|
|
134
|
+
|
|
135
|
+
return {
|
|
136
|
+
filename,
|
|
137
|
+
description
|
|
138
|
+
}
|
|
139
|
+
});
|
|
140
|
+
|
|
141
|
+
const path = this.getPath();
|
|
142
|
+
const block = this.loadBlockParameters(files);
|
|
143
|
+
const execution_context = this.getExecutionContext();
|
|
144
|
+
|
|
145
|
+
const page_operation = new LoadPageOperation(path, execution_context);
|
|
146
|
+
const page = await page_operation.perform();
|
|
147
|
+
|
|
148
|
+
const block_operation = new AddBlockOperation(
|
|
149
|
+
page,
|
|
150
|
+
block,
|
|
151
|
+
index_path,
|
|
152
|
+
execution_context
|
|
153
|
+
);
|
|
154
|
+
|
|
155
|
+
await block_operation.perform();
|
|
156
|
+
|
|
157
|
+
return `${path}?index_path=${index_path}&editing=${editing}`;
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
private async processCompleteBlock(): Promise<string> {
|
|
161
|
+
const path = this.getPath();
|
|
162
|
+
const body = this.getRequestBody() as CompleteBlockAction;
|
|
163
|
+
const {index_path} = body;
|
|
164
|
+
const execution_context = this.getExecutionContext();
|
|
165
|
+
const page_operation = new LoadPageOperation(path, execution_context);
|
|
166
|
+
const page = await page_operation.perform();
|
|
167
|
+
const original_block = getBlockAtIndexPath(page, index_path);
|
|
168
|
+
|
|
169
|
+
const todo_block = original_block as TodoBlock;
|
|
170
|
+
const {title} = todo_block;
|
|
171
|
+
const completed_at = Date.now();
|
|
172
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
173
|
+
|
|
174
|
+
const updated_block = {
|
|
175
|
+
...todo_block,
|
|
176
|
+
completed_at
|
|
177
|
+
};
|
|
178
|
+
|
|
179
|
+
const block_operation = new UpdateBlockOperation(
|
|
180
|
+
page,
|
|
181
|
+
updated_block,
|
|
182
|
+
index_path,
|
|
183
|
+
execution_context
|
|
184
|
+
);
|
|
185
|
+
|
|
186
|
+
await block_operation.perform();
|
|
187
|
+
|
|
188
|
+
return createToastPath(`${path}?index_path=${index_path}&editing=${editing}`, {
|
|
189
|
+
message: `${Emoji.COMPLETED_CHECKMARK} todo completed: ${title}`,
|
|
190
|
+
color: Color.GREEN
|
|
191
|
+
});
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
private async processEditBlock(): Promise<string> {
|
|
195
|
+
const filenames = await this.storeFiles();
|
|
196
|
+
const body = this.getRequestBody();
|
|
197
|
+
const action = body as AddBlockAction;
|
|
198
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
199
|
+
const {index_path} = action;
|
|
200
|
+
|
|
201
|
+
const files = filenames.map((filename) => {
|
|
202
|
+
const description = null;
|
|
203
|
+
|
|
204
|
+
return {
|
|
205
|
+
filename,
|
|
206
|
+
description
|
|
207
|
+
}
|
|
208
|
+
});
|
|
209
|
+
|
|
210
|
+
const path = this.getPath();
|
|
211
|
+
const block = this.loadBlockParameters(files);
|
|
212
|
+
const execution_context = this.getExecutionContext();
|
|
213
|
+
|
|
214
|
+
const page_operation = new LoadPageOperation(path, execution_context);
|
|
215
|
+
const page = await page_operation.perform();
|
|
216
|
+
|
|
217
|
+
const block_operation = new UpdateBlockOperation(
|
|
218
|
+
page,
|
|
219
|
+
block,
|
|
220
|
+
index_path,
|
|
221
|
+
execution_context
|
|
222
|
+
);
|
|
223
|
+
|
|
224
|
+
await block_operation.perform();
|
|
225
|
+
|
|
226
|
+
return `${path}?index_path=${index_path}&editing=${editing}`;
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
private loadBlockParameters(files: File[]): Block {
|
|
230
|
+
const action = this.getRequestBody() as AddBlockAction;
|
|
231
|
+
const {block_type} = action;
|
|
232
|
+
const created_at = Date.now();
|
|
233
|
+
const visibility = action.time_place_visibility;
|
|
234
|
+
|
|
235
|
+
const {create_role, read_role, update_role, delete_role} = action;
|
|
236
|
+
const permissions = {
|
|
237
|
+
[PermissionType.CREATE]: create_role,
|
|
238
|
+
[PermissionType.READ]: read_role,
|
|
239
|
+
[PermissionType.UPDATE]: update_role,
|
|
240
|
+
[PermissionType.DELETE]: delete_role
|
|
241
|
+
};
|
|
242
|
+
|
|
243
|
+
const [show_time, show_place] = (() => {
|
|
244
|
+
switch (visibility) {
|
|
245
|
+
case TimePlaceVisibility.NONE:
|
|
246
|
+
return [false, false];
|
|
247
|
+
|
|
248
|
+
case TimePlaceVisibility.PLACE:
|
|
249
|
+
return [false, true];
|
|
250
|
+
|
|
251
|
+
case TimePlaceVisibility.BOTH:
|
|
252
|
+
return [true, true];
|
|
253
|
+
|
|
254
|
+
case TimePlaceVisibility.TIME:
|
|
255
|
+
default:
|
|
256
|
+
return [true, false];
|
|
257
|
+
}
|
|
258
|
+
})();
|
|
259
|
+
|
|
260
|
+
switch (block_type) {
|
|
261
|
+
case BlockType.NOTE:
|
|
262
|
+
const add_note_action = action as AddNoteBlockAction;
|
|
263
|
+
|
|
264
|
+
const a: NoteBlock = {
|
|
265
|
+
block_type,
|
|
266
|
+
text: add_note_action.text,
|
|
267
|
+
show_time,
|
|
268
|
+
show_place,
|
|
269
|
+
created_at,
|
|
270
|
+
permissions
|
|
271
|
+
};
|
|
272
|
+
|
|
273
|
+
return a;
|
|
274
|
+
|
|
275
|
+
case BlockType.IMAGE:
|
|
276
|
+
const b: ImageBlock = {
|
|
277
|
+
block_type,
|
|
278
|
+
files,
|
|
279
|
+
show_time,
|
|
280
|
+
show_place,
|
|
281
|
+
created_at,
|
|
282
|
+
permissions
|
|
283
|
+
};
|
|
284
|
+
|
|
285
|
+
return b;
|
|
286
|
+
|
|
287
|
+
case BlockType.AUDIO:
|
|
288
|
+
const c: AudioBlock = {
|
|
289
|
+
block_type,
|
|
290
|
+
files,
|
|
291
|
+
show_time,
|
|
292
|
+
show_place,
|
|
293
|
+
created_at,
|
|
294
|
+
permissions
|
|
295
|
+
};
|
|
296
|
+
|
|
297
|
+
return c;
|
|
298
|
+
|
|
299
|
+
case BlockType.HEADER:
|
|
300
|
+
const add_header_action = action as AddHeaderBlockAction;
|
|
301
|
+
|
|
302
|
+
const d: HeaderBlock = {
|
|
303
|
+
block_type,
|
|
304
|
+
title: add_header_action.title,
|
|
305
|
+
created_at,
|
|
306
|
+
show_time: false,
|
|
307
|
+
show_place: false,
|
|
308
|
+
permissions
|
|
309
|
+
};
|
|
310
|
+
|
|
311
|
+
return d;
|
|
312
|
+
|
|
313
|
+
case BlockType.FOLDER:
|
|
314
|
+
const add_folder_action = action as AddFolderBlockAction;
|
|
315
|
+
const default_emoji = Emoji.FOLDER;
|
|
316
|
+
const default_color = Color.GREY;
|
|
317
|
+
|
|
318
|
+
const e: FolderBlock = {
|
|
319
|
+
block_type,
|
|
320
|
+
title: add_folder_action.title,
|
|
321
|
+
subtitle: add_folder_action.subtitle,
|
|
322
|
+
emoji: add_folder_action.emoji || default_emoji,
|
|
323
|
+
color: add_folder_action.color || default_color,
|
|
324
|
+
created_at,
|
|
325
|
+
show_time: false,
|
|
326
|
+
show_place: false,
|
|
327
|
+
permissions
|
|
328
|
+
};
|
|
329
|
+
|
|
330
|
+
return e;
|
|
331
|
+
|
|
332
|
+
case BlockType.MULTI_COLUMN:
|
|
333
|
+
const {max_columns} = action as AddMultiColumnBlockAction;
|
|
334
|
+
const parsed_columns = parseInt(max_columns.toString());
|
|
335
|
+
|
|
336
|
+
const f: MultiColumnBlock = {
|
|
337
|
+
block_type,
|
|
338
|
+
created_at,
|
|
339
|
+
show_time: false,
|
|
340
|
+
show_place: false,
|
|
341
|
+
max_columns: parsed_columns || 3,
|
|
342
|
+
children: [],
|
|
343
|
+
permissions
|
|
344
|
+
};
|
|
345
|
+
|
|
346
|
+
return f;
|
|
347
|
+
|
|
348
|
+
case BlockType.TODO:
|
|
349
|
+
const add_todo_action = action as AddTodoBlockAction;
|
|
350
|
+
|
|
351
|
+
const g: TodoBlock = {
|
|
352
|
+
block_type,
|
|
353
|
+
title: add_todo_action.title,
|
|
354
|
+
completed_at: null,
|
|
355
|
+
created_at,
|
|
356
|
+
show_time: false,
|
|
357
|
+
show_place: false,
|
|
358
|
+
permissions
|
|
359
|
+
};
|
|
360
|
+
|
|
361
|
+
return g;
|
|
362
|
+
|
|
363
|
+
case BlockType.LINK:
|
|
364
|
+
const add_link_action = action as AddLinkBlockAction;
|
|
365
|
+
|
|
366
|
+
const h: LinkBlock = {
|
|
367
|
+
block_type,
|
|
368
|
+
label: add_link_action.label,
|
|
369
|
+
href: add_link_action.href,
|
|
370
|
+
color: add_link_action.color,
|
|
371
|
+
show_time,
|
|
372
|
+
show_place,
|
|
373
|
+
created_at,
|
|
374
|
+
permissions
|
|
375
|
+
};
|
|
376
|
+
|
|
377
|
+
return h;
|
|
378
|
+
|
|
379
|
+
case BlockType.BACKGROUND:
|
|
380
|
+
const add_background_action = action as AddBackgroundBlockAction;
|
|
381
|
+
|
|
382
|
+
const i: BackgroundBlock = {
|
|
383
|
+
block_type,
|
|
384
|
+
color: add_background_action.color,
|
|
385
|
+
show_time,
|
|
386
|
+
show_place,
|
|
387
|
+
created_at,
|
|
388
|
+
permissions
|
|
389
|
+
};
|
|
390
|
+
|
|
391
|
+
return i;
|
|
392
|
+
|
|
393
|
+
case BlockType.WHITESPACE:
|
|
394
|
+
const add_whitespace_action = action as AddWhitespaceBlockAction;
|
|
395
|
+
|
|
396
|
+
const j: WhitespaceBlock = {
|
|
397
|
+
block_type,
|
|
398
|
+
line_count: add_whitespace_action.line_count,
|
|
399
|
+
show_time,
|
|
400
|
+
show_place,
|
|
401
|
+
created_at,
|
|
402
|
+
permissions
|
|
403
|
+
};
|
|
404
|
+
|
|
405
|
+
return j;
|
|
406
|
+
|
|
407
|
+
default:
|
|
408
|
+
throw new InvalidError(`
|
|
409
|
+
Unsupported block type: ${block_type}
|
|
410
|
+
`);
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
|
|
414
|
+
private async processDeleteBlock(): Promise<string> {
|
|
415
|
+
const body = this.getRequestBody();
|
|
416
|
+
const action = body as DeleteBlockAction;
|
|
417
|
+
const {index_path} = action;
|
|
418
|
+
const path = this.getPath();
|
|
419
|
+
const execution_context = this.getExecutionContext();
|
|
420
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
421
|
+
|
|
422
|
+
const operation = new DeleteBlockOperation(
|
|
423
|
+
path,
|
|
424
|
+
index_path,
|
|
425
|
+
execution_context
|
|
426
|
+
);
|
|
427
|
+
|
|
428
|
+
const previous_path = getPreviousIndexPath(index_path);
|
|
429
|
+
|
|
430
|
+
await operation.perform();
|
|
431
|
+
|
|
432
|
+
return createToastPath(`${path}?editing=${editing}&index_path=${previous_path}`, {
|
|
433
|
+
message: 'block deleted',
|
|
434
|
+
color: Color.FUSCHIA
|
|
435
|
+
});
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
private async processPromoteBlock(): Promise<string> {
|
|
439
|
+
const path = this.getPath();
|
|
440
|
+
const body = this.getRequestBody();
|
|
441
|
+
const action = body as PromoteBlockAction;
|
|
442
|
+
const {index_path} = action;
|
|
443
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
444
|
+
const execution_context = this.getExecutionContext();
|
|
445
|
+
const operation = new PromoteBlockOperation(path, index_path, execution_context);
|
|
446
|
+
const updated_path = await operation.perform();
|
|
447
|
+
|
|
448
|
+
return `${path}?index_path=${updated_path}&editing=${editing}`;
|
|
449
|
+
}
|
|
450
|
+
|
|
451
|
+
private async processDemoteBlock(): Promise<string> {
|
|
452
|
+
const path = this.getPath();
|
|
453
|
+
const body = this.getRequestBody();
|
|
454
|
+
const action = body as DemoteBlockAction;
|
|
455
|
+
const {index_path} = action;
|
|
456
|
+
const editing = this.getQueryParameter('editing') === 'true';
|
|
457
|
+
const execution_context = this.getExecutionContext();
|
|
458
|
+
const operation = new DemoteBlockOperation(path, index_path, execution_context);
|
|
459
|
+
const updated_path = await operation.perform();
|
|
460
|
+
|
|
461
|
+
return `${path}?index_path=${updated_path}&editing=${editing}`;
|
|
462
|
+
}
|
|
463
|
+
|
|
464
|
+
private getActionType(): ActionType {
|
|
465
|
+
const request_body = this.getRequestBody()
|
|
466
|
+
const fallback_value = this.getQueryParameter('action_type');
|
|
467
|
+
|
|
468
|
+
const action_type = request_body.action_type || fallback_value;
|
|
469
|
+
|
|
470
|
+
if (typeof action_type !== 'string') {
|
|
471
|
+
throw new InvalidError(`Invalid action_type: ${action_type}`);
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
const action_types = Object.values(ActionType);
|
|
475
|
+
|
|
476
|
+
if (!action_types.includes(action_type)) {
|
|
477
|
+
throw new InvalidError(`Invalid action_type: ${action_type}`);
|
|
478
|
+
}
|
|
479
|
+
|
|
480
|
+
return action_type as ActionType;
|
|
481
|
+
}
|
|
482
|
+
|
|
483
|
+
private getPath(): string {
|
|
484
|
+
const {path} = this.getRequestBody();
|
|
485
|
+
|
|
486
|
+
if (typeof path !== 'string') {
|
|
487
|
+
throw new InvalidError(`
|
|
488
|
+
Invalid path: ${path}
|
|
489
|
+
`);
|
|
490
|
+
}
|
|
491
|
+
|
|
492
|
+
return path;
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
private async storeFiles(): Promise<string[]> {
|
|
496
|
+
const action = this.getRequestBody();
|
|
497
|
+
const path = this.getPath();
|
|
498
|
+
const {files} = action as ActionWithFiles;
|
|
499
|
+
|
|
500
|
+
if (files === undefined) {
|
|
501
|
+
return [];
|
|
502
|
+
}
|
|
503
|
+
|
|
504
|
+
const execution_context = this.getExecutionContext();
|
|
505
|
+
const logger = execution_context.getLogger();
|
|
506
|
+
const {public_directory} = execution_context.getConfig();
|
|
507
|
+
const page_path = `${public_directory}${path}`;
|
|
508
|
+
|
|
509
|
+
await mkdir(page_path, {
|
|
510
|
+
recursive: true
|
|
511
|
+
});
|
|
512
|
+
|
|
513
|
+
const filenames: string[] = [];
|
|
514
|
+
|
|
515
|
+
let index = 0;
|
|
516
|
+
|
|
517
|
+
while (index < files.length) {
|
|
518
|
+
const file = files[index++];
|
|
519
|
+
|
|
520
|
+
if (file.size === 0) {
|
|
521
|
+
continue;
|
|
522
|
+
}
|
|
523
|
+
|
|
524
|
+
const new_filename = file.originalFilename;
|
|
525
|
+
const new_filepath = `${page_path}/${new_filename}`;
|
|
526
|
+
|
|
527
|
+
logger.info(`Moving upload: ${file.filepath} -> ${new_filepath}`);
|
|
528
|
+
|
|
529
|
+
try {
|
|
530
|
+
await copyFile(file.filepath, new_filepath);
|
|
531
|
+
await unlink(file.filepath);
|
|
532
|
+
} catch (error) {
|
|
533
|
+
logger.error(error as Error);
|
|
534
|
+
|
|
535
|
+
throw error;
|
|
536
|
+
}
|
|
537
|
+
|
|
538
|
+
filenames.push(new_filename);
|
|
539
|
+
}
|
|
540
|
+
|
|
541
|
+
return filenames;
|
|
542
|
+
}
|
|
543
|
+
}
|
|
544
|
+
|
|
545
|
+
export default CreateActionEndpoint;
|