From eae88828683ec05d438dd4908d86b73e67e9707d Mon Sep 17 00:00:00 2001 From: Sebastian Date: Fri, 27 Aug 2021 11:28:26 -0300 Subject: merchant backend pages --- packages/backend/.gitignore | 8 + .../.linaria-cache/src/pages/OfferTip.linaria.css | 2 + packages/backend/.storybook/.babelrc | 25 + packages/backend/.storybook/main.js | 82 + packages/backend/.storybook/preview.js | 73 + packages/backend/contrib/po2ts | 42 + packages/backend/copyleft-header.js | 15 + packages/backend/package.json | 142 + packages/backend/rollup.config.js | 100 + packages/backend/src/assets/empty.png | Bin 0 -> 2785 bytes .../src/assets/icons/android-chrome-192x192.png | Bin 0 -> 14058 bytes .../src/assets/icons/android-chrome-512x512.png | Bin 0 -> 51484 bytes .../backend/src/assets/icons/apple-touch-icon.png | Bin 0 -> 12746 bytes .../backend/src/assets/icons/favicon-16x16.png | Bin 0 -> 626 bytes .../backend/src/assets/icons/favicon-32x32.png | Bin 0 -> 1487 bytes packages/backend/src/assets/icons/languageicon.svg | 48 + .../backend/src/assets/icons/mstile-150x150.png | Bin 0 -> 9050 bytes packages/backend/src/context/backend.ts | 82 + packages/backend/src/context/config.ts | 32 + packages/backend/src/context/fetch.ts | 40 + packages/backend/src/context/instance.ts | 35 + packages/backend/src/context/listener.ts | 35 + packages/backend/src/context/translation.ts | 59 + packages/backend/src/css/pure-min.css | 973 ++++++ packages/backend/src/css/style.css | 62 + packages/backend/src/custom.d.ts | 40 + packages/backend/src/declaration.d.ts | 1384 ++++++++ packages/backend/src/hooks/async.ts | 76 + packages/backend/src/hooks/backend.ts | 262 ++ packages/backend/src/hooks/index.ts | 110 + packages/backend/src/hooks/instance.ts | 187 ++ packages/backend/src/hooks/listener.ts | 68 + packages/backend/src/hooks/notification.ts | 43 + packages/backend/src/hooks/notifications.ts | 48 + packages/backend/src/hooks/order.ts | 217 ++ packages/backend/src/hooks/product.ts | 199 ++ packages/backend/src/hooks/tips.ts | 159 + packages/backend/src/hooks/transfer.ts | 150 + packages/backend/src/i18n/de.po | 1057 ++++++ packages/backend/src/i18n/en.po | 1057 ++++++ packages/backend/src/i18n/es.po | 1065 ++++++ packages/backend/src/i18n/fr.po | 1057 ++++++ packages/backend/src/i18n/index.tsx | 203 ++ packages/backend/src/i18n/it.po | 1057 ++++++ packages/backend/src/i18n/poheader | 27 + packages/backend/src/i18n/strings-prelude | 19 + packages/backend/src/i18n/strings.ts | 3445 ++++++++++++++++++++ packages/backend/src/i18n/sv.po | 1057 ++++++ .../backend/src/i18n/taler-merchant-backoffice.pot | 1054 ++++++ packages/backend/src/index.tsx | 67 + packages/backend/src/pages/DepletedTip.stories.tsx | 40 + packages/backend/src/pages/DepletedTip.tsx | 45 + packages/backend/src/pages/OfferRefund.stories.tsx | 40 + packages/backend/src/pages/OfferRefund.tsx | 103 + packages/backend/src/pages/OfferTip.stories.tsx | 40 + packages/backend/src/pages/OfferTip.tsx | 113 + .../backend/src/pages/RequestPayment.stories.tsx | 40 + packages/backend/src/pages/RequestPayment.tsx | 125 + .../backend/src/pages/ShowOrderDetails.stories.tsx | 40 + packages/backend/src/pages/ShowOrderDetails.tsx | 125 + packages/backend/src/utils/amount.ts | 69 + packages/backend/src/utils/constants.ts | 47 + packages/backend/src/utils/table.ts | 37 + packages/backend/src/utils/types.ts | 31 + packages/backend/tests/__mocks__/browserMocks.ts | 42 + packages/backend/tests/__mocks__/fileMocks.ts | 24 + .../backend/tests/__mocks__/fileTransformer.js | 31 + packages/backend/tests/__mocks__/setupTests.ts | 28 + packages/backend/tests/funcitons/regex.test.ts | 87 + packages/backend/tests/util.ts | 62 + packages/backend/tsconfig.back.json | 23 + packages/backend/tsconfig.json | 61 + packages/backend/tsconfig.tsbuildinfo | 2147 ++++++++++++ 73 files changed, 19363 insertions(+) create mode 100644 packages/backend/.gitignore create mode 100644 packages/backend/.linaria-cache/src/pages/OfferTip.linaria.css create mode 100644 packages/backend/.storybook/.babelrc create mode 100644 packages/backend/.storybook/main.js create mode 100644 packages/backend/.storybook/preview.js create mode 100755 packages/backend/contrib/po2ts create mode 100644 packages/backend/copyleft-header.js create mode 100644 packages/backend/package.json create mode 100644 packages/backend/rollup.config.js create mode 100644 packages/backend/src/assets/empty.png create mode 100644 packages/backend/src/assets/icons/android-chrome-192x192.png create mode 100644 packages/backend/src/assets/icons/android-chrome-512x512.png create mode 100644 packages/backend/src/assets/icons/apple-touch-icon.png create mode 100644 packages/backend/src/assets/icons/favicon-16x16.png create mode 100644 packages/backend/src/assets/icons/favicon-32x32.png create mode 100644 packages/backend/src/assets/icons/languageicon.svg create mode 100644 packages/backend/src/assets/icons/mstile-150x150.png create mode 100644 packages/backend/src/context/backend.ts create mode 100644 packages/backend/src/context/config.ts create mode 100644 packages/backend/src/context/fetch.ts create mode 100644 packages/backend/src/context/instance.ts create mode 100644 packages/backend/src/context/listener.ts create mode 100644 packages/backend/src/context/translation.ts create mode 100644 packages/backend/src/css/pure-min.css create mode 100644 packages/backend/src/css/style.css create mode 100644 packages/backend/src/custom.d.ts create mode 100644 packages/backend/src/declaration.d.ts create mode 100644 packages/backend/src/hooks/async.ts create mode 100644 packages/backend/src/hooks/backend.ts create mode 100644 packages/backend/src/hooks/index.ts create mode 100644 packages/backend/src/hooks/instance.ts create mode 100644 packages/backend/src/hooks/listener.ts create mode 100644 packages/backend/src/hooks/notification.ts create mode 100644 packages/backend/src/hooks/notifications.ts create mode 100644 packages/backend/src/hooks/order.ts create mode 100644 packages/backend/src/hooks/product.ts create mode 100644 packages/backend/src/hooks/tips.ts create mode 100644 packages/backend/src/hooks/transfer.ts create mode 100644 packages/backend/src/i18n/de.po create mode 100644 packages/backend/src/i18n/en.po create mode 100644 packages/backend/src/i18n/es.po create mode 100644 packages/backend/src/i18n/fr.po create mode 100644 packages/backend/src/i18n/index.tsx create mode 100644 packages/backend/src/i18n/it.po create mode 100644 packages/backend/src/i18n/poheader create mode 100644 packages/backend/src/i18n/strings-prelude create mode 100644 packages/backend/src/i18n/strings.ts create mode 100644 packages/backend/src/i18n/sv.po create mode 100644 packages/backend/src/i18n/taler-merchant-backoffice.pot create mode 100644 packages/backend/src/index.tsx create mode 100644 packages/backend/src/pages/DepletedTip.stories.tsx create mode 100644 packages/backend/src/pages/DepletedTip.tsx create mode 100644 packages/backend/src/pages/OfferRefund.stories.tsx create mode 100644 packages/backend/src/pages/OfferRefund.tsx create mode 100644 packages/backend/src/pages/OfferTip.stories.tsx create mode 100644 packages/backend/src/pages/OfferTip.tsx create mode 100644 packages/backend/src/pages/RequestPayment.stories.tsx create mode 100644 packages/backend/src/pages/RequestPayment.tsx create mode 100644 packages/backend/src/pages/ShowOrderDetails.stories.tsx create mode 100644 packages/backend/src/pages/ShowOrderDetails.tsx create mode 100644 packages/backend/src/utils/amount.ts create mode 100644 packages/backend/src/utils/constants.ts create mode 100644 packages/backend/src/utils/table.ts create mode 100644 packages/backend/src/utils/types.ts create mode 100644 packages/backend/tests/__mocks__/browserMocks.ts create mode 100644 packages/backend/tests/__mocks__/fileMocks.ts create mode 100644 packages/backend/tests/__mocks__/fileTransformer.js create mode 100644 packages/backend/tests/__mocks__/setupTests.ts create mode 100644 packages/backend/tests/funcitons/regex.test.ts create mode 100644 packages/backend/tests/util.ts create mode 100644 packages/backend/tsconfig.back.json create mode 100644 packages/backend/tsconfig.json create mode 100644 packages/backend/tsconfig.tsbuildinfo (limited to 'packages/backend') diff --git a/packages/backend/.gitignore b/packages/backend/.gitignore new file mode 100644 index 0000000..db8559a --- /dev/null +++ b/packages/backend/.gitignore @@ -0,0 +1,8 @@ +/build +/size-plugin.json +/storybook-static +/docs +/single +/coverage +/dist +/.rollup.cache diff --git a/packages/backend/.linaria-cache/src/pages/OfferTip.linaria.css b/packages/backend/.linaria-cache/src/pages/OfferTip.linaria.css new file mode 100644 index 0000000..9ba2add --- /dev/null +++ b/packages/backend/.linaria-cache/src/pages/OfferTip.linaria.css @@ -0,0 +1,2 @@ +.d54jv91{background-color:red;} +/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNyYy9wYWdlcy9PZmZlclRpcC50c3giXSwibmFtZXMiOlsiLmQ1NGp2OTEiXSwibWFwcGluZ3MiOiJBQTJCTUEiLCJmaWxlIjoic3JjL3BhZ2VzL09mZmVyVGlwLnRzeCIsInNvdXJjZXNDb250ZW50IjpbIi8qXG4gVGhpcyBmaWxlIGlzIHBhcnQgb2YgR05VIFRhbGVyXG4gKEMpIDIwMjEgVGFsZXIgU3lzdGVtcyBTLkEuXG5cbiBHTlUgVGFsZXIgaXMgZnJlZSBzb2Z0d2FyZTsgeW91IGNhbiByZWRpc3RyaWJ1dGUgaXQgYW5kL29yIG1vZGlmeSBpdCB1bmRlciB0aGVcbiB0ZXJtcyBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYXMgcHVibGlzaGVkIGJ5IHRoZSBGcmVlIFNvZnR3YXJlXG4gRm91bmRhdGlvbjsgZWl0aGVyIHZlcnNpb24gMywgb3IgKGF0IHlvdXIgb3B0aW9uKSBhbnkgbGF0ZXIgdmVyc2lvbi5cblxuIEdOVSBUYWxlciBpcyBkaXN0cmlidXRlZCBpbiB0aGUgaG9wZSB0aGF0IGl0IHdpbGwgYmUgdXNlZnVsLCBidXQgV0lUSE9VVCBBTllcbiBXQVJSQU5UWTsgd2l0aG91dCBldmVuIHRoZSBpbXBsaWVkIHdhcnJhbnR5IG9mIE1FUkNIQU5UQUJJTElUWSBvciBGSVRORVNTIEZPUlxuIEEgUEFSVElDVUxBUiBQVVJQT1NFLiAgU2VlIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBmb3IgbW9yZSBkZXRhaWxzLlxuXG4gWW91IHNob3VsZCBoYXZlIHJlY2VpdmVkIGEgY29weSBvZiB0aGUgR05VIEdlbmVyYWwgUHVibGljIExpY2Vuc2UgYWxvbmcgd2l0aFxuIEdOVSBUYWxlcjsgc2VlIHRoZSBmaWxlIENPUFlJTkcuICBJZiBub3QsIHNlZSA8aHR0cDovL3d3dy5nbnUub3JnL2xpY2Vuc2VzLz5cbiAqL1xuXG4vKipcbipcbiogQGF1dGhvciBTZWJhc3RpYW4gSmF2aWVyIE1hcmNoYW5vIChzZWJhc2ptKVxuKi9cbmltcG9ydCB7IHJlbmRlciwgaCwgVk5vZGUsIEZyYWdtZW50IH0gZnJvbSAncHJlYWN0JztcbmltcG9ydCB7IHVzZUVmZmVjdCB9IGZyb20gJ3ByZWFjdC9ob29rcyc7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tIFwiQGxpbmFyaWEvcmVhY3RcIlxuaW1wb3J0IFwiLi4vY3NzL3B1cmUtbWluLmNzc1wiXG5pbXBvcnQgXCIuLi9jc3Mvc3R5bGUuY3NzXCJcblxuXG5jb25zdCBEaXZSZWQgPSBzdHlsZWQuZGl2YFxuICBiYWNrZ3JvdW5kLWNvbG9yOiByZWQ7XG5gO1xuXG5leHBvcnQgZnVuY3Rpb24gT2ZmZXJUaXAoKTogVk5vZGUge1xuICB1c2VFZmZlY3QoKCkgPT4ge1xuICAgIGNvbnN0IGNoZWNrVXJsID0gXCJ7eyYgdGlwX3N0YXR1c191cmwgfX1cIjtcbiAgICBjb25zdCBkZWxheU1zID0gNTAwO1xuICAgIGZ1bmN0aW9uIGNoZWNrKCkge1xuICAgICAgbGV0IHJldHJpZWQgPSBmYWxzZTtcbiAgICAgIGZ1bmN0aW9uIHJldHJ5T25jZSgpIHtcbiAgICAgICAgaWYgKCFyZXRyaWVkKSB7XG4gICAgICAgICAgcmV0cmllZCA9IHRydWU7XG4gICAgICAgICAgY2hlY2soKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgY29uc3QgcmVxID0gbmV3IFhNTEh0dHBSZXF1ZXN0KCk7XG4gICAgICByZXEub25yZWFkeXN0YXRlY2hhbmdlID0gZnVuY3Rpb24gKCkge1xuICAgICAgICBpZiAocmVxLnJlYWR5U3RhdGUgPT09IFhNTEh0dHBSZXF1ZXN0LkRPTkUpIHtcbiAgICAgICAgICBpZiAocmVxLnN0YXR1cyA9PT0gNDEwKSB7XG4gICAgICAgICAgICB3aW5kb3cubG9jYXRpb24ucmVsb2FkKHRydWUpO1xuICAgICAgICAgIH1cbiAgICAgICAgICBzZXRUaW1lb3V0KHJldHJ5T25jZSwgZGVsYXlNcyk7XG4gICAgICAgIH1cbiAgICAgIH07XG4gICAgICByZXEub25lcnJvciA9IGZ1bmN0aW9uICgpIHtcbiAgICAgICAgc2V0VGltZW91dChyZXRyeU9uY2UsIGRlbGF5TXMpO1xuICAgICAgfVxuICAgICAgLy8gcmVxLm9wZW4oXCJHRVRcIiwgY2hlY2tVcmwpO1xuICAgICAgcmVxLnNlbmQoKTtcbiAgICB9XG5cbiAgICAvLyBzZXRUaW1lb3V0KGNoZWNrLCBkZWxheU1zKTtcbiAgfSlcbiAgcmV0dXJuIDxGcmFnbWVudD5cbiAgPHNlY3Rpb24gaWQ9XCJtYWluXCIgY2xhc3M9XCJjb250ZW50XCI+XG4gICAgPGgxPkNvbGxlY3QgVGFsZXIgdGlwPC9oMT5cbiAgICA8ZGl2IGNsYXNzPVwidGFsZXItaW5zdGFsbGVkLWhpZGVcIj5cbiAgICAgIDxwPlxuICAgICAgICBTY2FuIHRoaXMgUVIgY29kZSB3aXRoIHlvdXIgVGFsZXIgbW9iaWxlIHdhbGxldDpcbiAgICAgIDwvcD5cbiAgICAgIDxkaXYgY2xhc3M9XCJxclwiPlxuICAgICAgICB7Lyoge3t7dGFsZXJfdGlwX3FyY29kZV9zdmd9fX0gKi99XG4gICAgICA8L2Rpdj5cbiAgICAgIDxwPlxuICAgICAgICA8YnV0dG9uIG9uQ2xpY2s9eygpID0+IHtcbiAgICAgICAgICAvLyB3aW5kb3cubG9jYXRpb24uaHJlZiA9ICd7e3RhbGVyX3JlZnVuZF91cml9fSdcbiAgICAgICAgfX0+XG4gICAgICAgICAgT3Igb3BlbiB5b3VyIFRhbGxlciB3YWxsZXRcbiAgICAgICAgPC9idXR0b24+XG4gICAgICA8L3A+XG4gICAgICA8cD5cbiAgICAgICAgPGEgaHJlZj1cImh0dHBzOi8vd2FsbGV0LnRhbGVyLm5ldC9cIj5Eb24ndCBoYXZlIGEgVGFsZXIgd2FsbGV0IHlldD8gSW5zdGFsbCBpdCE8L2E+XG4gICAgICA8L3A+XG4gICAgPC9kaXY+XG4gICAgPGhyIC8+XG4gICAgPERpdlJlZD5cbiAgICAgIHRoaXMgYmFja2dyb3VuZCBpcyByZWRhc2RzYVxuICAgIDwvRGl2UmVkPlxuICA8L3NlY3Rpb24+XG4gIDxGb290ZXIgLz5cbiAgPC9GcmFnbWVudD5cbn1cblxuZnVuY3Rpb24gRm9vdGVyKCkge1xuICByZXR1cm4gPGRpdiBjbGFzcz1cInRhbGVyYmFyXCI+XG4gICAgPHA+WW91IGNhbiBsZWFybiBtb3JlIGFib3V0IEdOVSBUYWxlciBvbiBvdXIgPGEgaHJlZj1cImh0dHBzOi8vdGFsZXIubmV0L1wiPndlYnNpdGU8L2E+LjxiciAvPlxuICAgICAgQ29weXJpZ2h0ICZjb3B5OyAyMDE0Jm1kYXNoOzIwMjEgVGFsZXIgU3lzdGVtcyBTQTwvcD5cbiAgPC9kaXY+XG59XG5cblxuZXhwb3J0IGZ1bmN0aW9uIFRpdGxlKCk6IFZOb2RlIHtcbiAgcmV0dXJuIDx0aXRsZT5UaXAgYXZhaWxhYmxlPC90aXRsZT5cbn1cblxuZXhwb3J0IGZ1bmN0aW9uIG1haW4oKTogdm9pZCB7XG4gIHRyeSB7XG4gICAgcmVuZGVyKDxPZmZlclRpcCAvPiwgZG9jdW1lbnQuYm9keSk7XG4gIH0gY2F0Y2ggKGUpIHtcbiAgICBjb25zb2xlLmVycm9yKFwiZ290IGVycm9yXCIsIGUpO1xuICAgIGRvY3VtZW50LmJvZHkuaW5uZXJUZXh0ID0gYEZhdGFsIGVycm9yOiBcIiR7ZS5tZXNzYWdlfVwiLiAgUGxlYXNlIHJlcG9ydCB0aGlzIGJ1ZyBhdCBodHRwczovL2J1Z3MuZ251bmV0Lm9yZy8uYDtcbiAgfVxufVxuXG4iXX0=*/ \ No newline at end of file diff --git a/packages/backend/.storybook/.babelrc b/packages/backend/.storybook/.babelrc new file mode 100644 index 0000000..610b6f3 --- /dev/null +++ b/packages/backend/.storybook/.babelrc @@ -0,0 +1,25 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + + /** + * + * @author Sebastian Javier Marchano (sebasjm) + */ +{ + "presets": [ + "preact-cli/babel" + ] +} \ No newline at end of file diff --git a/packages/backend/.storybook/main.js b/packages/backend/.storybook/main.js new file mode 100644 index 0000000..5497a65 --- /dev/null +++ b/packages/backend/.storybook/main.js @@ -0,0 +1,82 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + + +module.exports = { + "stories": [ + "../src/**/*.stories.mdx", + "../src/**/*.stories.@(js|jsx|ts|tsx)" + ], + "addons": [ + "@storybook/preset-scss", + "@storybook/addon-a11y", + "@storybook/addon-essentials" //docs, control, actions, viewpot, toolbar, background + ], + // sb does not yet support new jsx transform by default + // https://github.com/storybookjs/storybook/issues/12881 + // https://github.com/storybookjs/storybook/issues/12952 + babel: async (options) => ({ + ...options, + presets: [ + ...options.presets, + [ + '@babel/preset-react', { + runtime: 'automatic', + }, + 'preset-react-jsx-transform' + ], + "@linaria", + ], + }), + webpackFinal: (config) => { + // should be removed after storybook 6.3 + // https://github.com/storybookjs/storybook/issues/12853#issuecomment-821576113 + config.resolve.alias = { + react: "preact/compat", + "react-dom": "preact/compat", + }; + + // we need to add @linaria loader AFTER the babel-loader + // https://github.com/callstack/linaria/blob/master/docs/BUNDLERS_INTEGRATION.md#webpack + config.module.rules[0] = { + ...(config.module.rules[0]), + loader: undefined, // Disable the predefined babel-loader on the rule + use: [ + { + ...(config.module.rules[0].use[0]), + loader: 'babel-loader', + }, + { + loader: '@linaria/webpack-loader', + options: { + sourceMap: true, //always true since this is dev + babelOptions: { + presets: config.module.rules[0].use[0].options.presets, + } + // Pass the current babel options to linaria's babel instance + } + } + ] + }; + + return config; + }, +} \ No newline at end of file diff --git a/packages/backend/.storybook/preview.js b/packages/backend/.storybook/preview.js new file mode 100644 index 0000000..a9cc4c3 --- /dev/null +++ b/packages/backend/.storybook/preview.js @@ -0,0 +1,73 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +import { ConfigContextProvider } from '../src/context/config' +import { InstanceContextProvider } from '../src/context/instance' +import { TranslationProvider } from '../src/context/translation' +import { BackendContextProvider } from '../src/context/backend' +import { h } from 'preact'; + +const mockConfig = { + backendURL: 'http://demo.taler.net', + currency: 'TESTKUDOS' +} + +const mockInstance = { + id: 'instance-id', + token: 'instance-token', + admin: false, +} + +const mockBackend = { + url: 'http://merchant.url', + token: 'default-token', + triedToLog: false, +} + +export const parameters = { + controls: { expanded: true }, + // actions: { argTypesRegex: "^on.*" }, +} + +export const globalTypes = { + locale: { + name: 'Locale', + description: 'Internationalization locale', + defaultValue: 'en', + toolbar: { + icon: 'globe', + items: [ + { value: 'en', right: 'πŸ‡ΊπŸ‡Έ', title: 'English' }, + { value: 'es', right: 'πŸ‡ͺπŸ‡Έ', title: 'Spanish' }, + ], + }, + }, +}; + +export const decorators = [ + (Story, { globals }) => + + , + (Story) => + + , + (Story) => + + , + (Story) => + + , +]; diff --git a/packages/backend/contrib/po2ts b/packages/backend/contrib/po2ts new file mode 100755 index 0000000..a135da6 --- /dev/null +++ b/packages/backend/contrib/po2ts @@ -0,0 +1,42 @@ +#!/usr/bin/env node +/* + This file is part of GNU Taler + (C) 2020 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** + * Convert a .po file into a JavaScript / TypeScript expression. + */ + +const po2json = require("po2json"); + +const filename = process.argv[2]; + +if (!filename) { + console.error("error: missing filename"); + process.exit(1); +} + +const m = filename.match(/([a-zA-Z0-9-_]+).po/); + +if (!m) { + console.error("error: unexpected filename (expected .po)"); + process.exit(1); +} + +const lang = m[1]; +const pojson = po2json.parseFileSync(filename, { format: "jed1.x", fuzzy: true }); +const s = + "strings['" + lang + "'] = " + JSON.stringify(pojson, null, " ") + ";\n"; +console.log(s); diff --git a/packages/backend/copyleft-header.js b/packages/backend/copyleft-header.js new file mode 100644 index 0000000..0794cb8 --- /dev/null +++ b/packages/backend/copyleft-header.js @@ -0,0 +1,15 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ diff --git a/packages/backend/package.json b/packages/backend/package.json new file mode 100644 index 0000000..6a78f5f --- /dev/null +++ b/packages/backend/package.json @@ -0,0 +1,142 @@ +{ + "private": true, + "name": "merchant-backend", + "version": "0.0.4", + "license": "MIT", + "scripts": { + "build": "rollup -c", + "compile": "tsc", + "dev": "rollup -c -w", + "lint-check": "eslint '{src,tests}/**/*.{js,jsx,ts,tsx}'", + "lint-fix": "eslint --fix '{src,tests}/**/*.{js,jsx,ts,tsx}'", + "test": "jest ./tests", + "dev-test": "jest ./tests --watch", + "typedoc": "typedoc src", + "clean": "rimraf build storybook-static docs single", + "serve-dist": "sirv --port ${PORT:=8080} --cors --single dist", + "build-storybook": "build-storybook", + "storybook": "start-storybook -p 6006" + }, + "engines": { + "node": ">=12", + "pnpm": ">=5" + }, + "eslintConfig": { + "parser": "@typescript-eslint/parser", + "extends": [ + "preact", + "plugin:@typescript-eslint/recommended" + ], + "plugins": [ + "header" + ], + "rules": { + "header/header": [ + 2, + "copyleft-header.js" + ] + }, + "ignorePatterns": [ + "build/" + ] + }, + "dependencies": { + "@gnu-taler/taler-util": "0.8.3", + "axios": "^0.21.1", + "date-fns": "^2.21.1", + "history": "4.10.1", + "jed": "^1.1.1", + "preact": "^10.5.13", + "preact-router": "^3.2.1", + "qrcode-generator": "^1.4.4", + "swr": "^0.5.5", + "yup": "^0.32.9" + }, + "devDependencies": { + "@babel/core": "^7.13.16", + "@babel/plugin-transform-react-jsx-source": "^7.12.13", + "@creativebulma/bulma-tooltip": "^1.2.0", + "@gnu-taler/pogen": "^0.0.5", + "@linaria/babel-preset": "^3.0.0-beta.4", + "@linaria/core": "^3.0.0-beta.4", + "@linaria/react": "^3.0.0-beta.7", + "@linaria/rollup": "^3.0.0-beta.7", + "@linaria/shaker": "^3.0.0-beta.7", + "@linaria/webpack-loader": "^3.0.0-beta.7", + "@rollup/plugin-alias": "^3.1.5", + "@rollup/plugin-babel": "^5.3.0", + "@rollup/plugin-commonjs": "^20.0.0", + "@rollup/plugin-html": "^0.2.3", + "@rollup/plugin-image": "^2.1.1", + "@rollup/plugin-json": "^4.1.0", + "@rollup/plugin-replace": "^3.0.0", + "@rollup/plugin-typescript": "^8.2.5", + "@storybook/addon-a11y": "^6.2.9", + "@storybook/addon-actions": "^6.2.9", + "@storybook/addon-essentials": "^6.2.9", + "@storybook/addon-links": "^6.2.9", + "@storybook/preact": "^6.2.9", + "@storybook/preset-scss": "^1.0.3", + "@testing-library/preact": "^2.0.1", + "@testing-library/preact-hooks": "^1.1.0", + "@types/enzyme": "^3.10.8", + "@types/history": "^4.7.8", + "@types/jest": "^26.0.23", + "@types/mocha": "^8.2.2", + "@typescript-eslint/eslint-plugin": "^4.22.0", + "@typescript-eslint/parser": "^4.22.0", + "babel-loader": "^8.2.2", + "base64-inline-loader": "^1.1.1", + "bulma": "^0.9.2", + "bulma-checkbox": "^1.1.1", + "bulma-radio": "^1.1.1", + "bulma-responsive-tables": "^1.2.3", + "bulma-switch-control": "^1.1.1", + "bulma-timeline": "^3.0.4", + "bulma-upload-control": "^1.2.0", + "dotenv": "^8.2.0", + "enzyme": "^3.11.0", + "enzyme-adapter-preact-pure": "^3.1.0", + "eslint": "^7.25.0", + "eslint-config-preact": "^1.1.4", + "eslint-plugin-header": "^3.1.1", + "html-webpack-inline-chunk-plugin": "^1.1.1", + "html-webpack-inline-source-plugin": "0.0.10", + "html-webpack-skip-assets-plugin": "^1.0.1", + "inline-chunk-html-plugin": "^1.1.1", + "jest": "^26.6.3", + "jest-preset-preact": "^4.0.2", + "po2json": "^0.4.5", + "preact-cli": "^3.0.5", + "preact-render-to-json": "^3.6.6", + "preact-render-to-string": "^5.1.19", + "rimraf": "^3.0.2", + "rollup": "^2.56.3", + "rollup-plugin-bundle-html": "^0.2.2", + "rollup-plugin-css-only": "^3.1.0", + "sass": "^1.32.13", + "sass-loader": "10.1.1", + "script-ext-html-webpack-plugin": "^2.1.5", + "sirv-cli": "^1.0.11", + "tslib": "^2.3.1", + "typedoc": "^0.20.36", + "typescript": "^4.2.4" + }, + "jest": { + "preset": "jest-preset-preact", + "transformIgnorePatterns": [ + "node_modules/.pnpm/(?!(@gnu-taler\\+taler-util))", + "\\.pnp\\.[^\\/]+$" + ], + "setupFiles": [ + "/tests/__mocks__/browserMocks.ts", + "/tests/__mocks__/setupTests.ts" + ], + "moduleNameMapper": { + "\\.(css|less)$": "identity-obj-proxy" + }, + "transform": { + "\\.(jpg|jpeg|png|gif|eot|otf|webp|svg|ttf|woff|woff2|mp4|webm|wav|mp3|m4a|aac|oga|po)$": "/tests/__mocks__/fileTransformer.js" + } + } +} diff --git a/packages/backend/rollup.config.js b/packages/backend/rollup.config.js new file mode 100644 index 0000000..9051adc --- /dev/null +++ b/packages/backend/rollup.config.js @@ -0,0 +1,100 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +// rollup.config.js +import linaria from '@linaria/rollup'; +import nodeResolve from "@rollup/plugin-node-resolve"; +import alias from "@rollup/plugin-alias"; +import image from '@rollup/plugin-image'; +import json from "@rollup/plugin-json"; +import ts from "@rollup/plugin-typescript"; +import replace from "@rollup/plugin-replace"; +import css from 'rollup-plugin-css-only'; +import html from '@rollup/plugin-html'; + + + +const template = async ({ + files, + title +}) => { + const scripts = (files.js || []).map(({ code }) => ``).join('\n'); + const css = (files.css || []).map(({ source }) => ``).join('\n'); + return ` + + + + ${title} + ${css} + + + ${scripts} + + +`; +}; + +const makePlugins = (name) => [ + alias({ + entries: [ + { find: 'react', replacement: 'preact/compat' }, + { find: 'react-dom', replacement: 'preact/compat' } + ] + }), + + replace({ + "process.env.NODE_ENV": JSON.stringify("production"), + preventAssignment: true, + }), + + nodeResolve({ + browser: true, + preferBuiltins: true, + }), + + json(), + image(), + + linaria({ + sourceMap: process.env.NODE_ENV !== 'production', + }), + css(), + ts({ + sourceMap: false, + outputToFilesystem: false, + }), + html({ template, fileName: name }), +]; + + +const pageDefinition = (name) => ({ + input: `src/pages/${name}.tsx`, + output: { + file: `dist/pages/${name}.js`, + format: "iife", + exports: 'named', + name: 'page', + }, + plugins: makePlugins(`${name}.html`), +}); + +export default [ + pageDefinition("OfferTip"), + pageDefinition("OfferRefund"), + pageDefinition("DepletedTip"), + pageDefinition("RequestPayment"), + pageDefinition("ShowOrderDetails"), +] diff --git a/packages/backend/src/assets/empty.png b/packages/backend/src/assets/empty.png new file mode 100644 index 0000000..5120d31 Binary files /dev/null and b/packages/backend/src/assets/empty.png differ diff --git a/packages/backend/src/assets/icons/android-chrome-192x192.png b/packages/backend/src/assets/icons/android-chrome-192x192.png new file mode 100644 index 0000000..93ebe2e Binary files /dev/null and b/packages/backend/src/assets/icons/android-chrome-192x192.png differ diff --git a/packages/backend/src/assets/icons/android-chrome-512x512.png b/packages/backend/src/assets/icons/android-chrome-512x512.png new file mode 100644 index 0000000..52d1623 Binary files /dev/null and b/packages/backend/src/assets/icons/android-chrome-512x512.png differ diff --git a/packages/backend/src/assets/icons/apple-touch-icon.png b/packages/backend/src/assets/icons/apple-touch-icon.png new file mode 100644 index 0000000..254e4bb Binary files /dev/null and b/packages/backend/src/assets/icons/apple-touch-icon.png differ diff --git a/packages/backend/src/assets/icons/favicon-16x16.png b/packages/backend/src/assets/icons/favicon-16x16.png new file mode 100644 index 0000000..e81177d Binary files /dev/null and b/packages/backend/src/assets/icons/favicon-16x16.png differ diff --git a/packages/backend/src/assets/icons/favicon-32x32.png b/packages/backend/src/assets/icons/favicon-32x32.png new file mode 100644 index 0000000..40e9b5b Binary files /dev/null and b/packages/backend/src/assets/icons/favicon-32x32.png differ diff --git a/packages/backend/src/assets/icons/languageicon.svg b/packages/backend/src/assets/icons/languageicon.svg new file mode 100644 index 0000000..22d58da --- /dev/null +++ b/packages/backend/src/assets/icons/languageicon.svg @@ -0,0 +1,48 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/backend/src/assets/icons/mstile-150x150.png b/packages/backend/src/assets/icons/mstile-150x150.png new file mode 100644 index 0000000..9cfb889 Binary files /dev/null and b/packages/backend/src/assets/icons/mstile-150x150.png differ diff --git a/packages/backend/src/context/backend.ts b/packages/backend/src/context/backend.ts new file mode 100644 index 0000000..a920d6f --- /dev/null +++ b/packages/backend/src/context/backend.ts @@ -0,0 +1,82 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { createContext, h, VNode } from 'preact' +import { useCallback, useContext, useState } from 'preact/hooks' +import { useBackendDefaultToken, useBackendURL } from '../hooks'; + +interface BackendContextType { + url: string; + token?: string; + triedToLog: boolean; + resetBackend: () => void; + clearAllTokens: () => void; + addTokenCleaner: (c: () => void) => void; + updateLoginStatus: (url: string, token?: string) => void; +} + +const BackendContext = createContext({ + url: '', + token: undefined, + triedToLog: false, + resetBackend: () => null, + clearAllTokens: () => null, + addTokenCleaner: () => null, + updateLoginStatus: () => null, +}) + +function useBackendContextState(defaultUrl?: string): BackendContextType { + const [url, triedToLog, changeBackend, resetBackend] = useBackendURL(defaultUrl); + const [token, _updateToken] = useBackendDefaultToken(); + const updateToken = (t?: string) => { + _updateToken(t) + } + + const tokenCleaner = useCallback(() => { updateToken(undefined) }, []) + const [cleaners, setCleaners] = useState([tokenCleaner]) + const addTokenCleaner = (c: () => void) => setCleaners(cs => [...cs, c]) + const addTokenCleanerMemo = useCallback((c: () => void) => { addTokenCleaner(c) }, [tokenCleaner]) + + const clearAllTokens = () => { + cleaners.forEach(c => c()) + for (let i = 0; i < localStorage.length; i++) { + const k = localStorage.key(i) + if (k && /^backend-token/.test(k)) localStorage.removeItem(k) + } + resetBackend() + } + + const updateLoginStatus = (url: string, token?: string) => { + changeBackend(url); + if (token) updateToken(token); + }; + + + return { url, token, triedToLog, updateLoginStatus, resetBackend, clearAllTokens, addTokenCleaner: addTokenCleanerMemo } +} + +export const BackendContextProvider = ({ children, defaultUrl }: { children: any, defaultUrl?: string }): VNode => { + const value = useBackendContextState(defaultUrl) + + return h(BackendContext.Provider, { value, children }); +} + +export const useBackendContext = (): BackendContextType => useContext(BackendContext); diff --git a/packages/backend/src/context/config.ts b/packages/backend/src/context/config.ts new file mode 100644 index 0000000..5cd7723 --- /dev/null +++ b/packages/backend/src/context/config.ts @@ -0,0 +1,32 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { createContext } from 'preact' +import { useContext } from 'preact/hooks' + +interface Type { + currency: string; + version: string; +} +const Context = createContext(null!) + +export const ConfigContextProvider = Context.Provider +export const useConfigContext = (): Type => useContext(Context); diff --git a/packages/backend/src/context/fetch.ts b/packages/backend/src/context/fetch.ts new file mode 100644 index 0000000..52a4f9c --- /dev/null +++ b/packages/backend/src/context/fetch.ts @@ -0,0 +1,40 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { h, createContext, VNode, ComponentChildren } from 'preact' +import { useContext } from 'preact/hooks' +import useSWR, { trigger, useSWRInfinite, cache, mutate } from 'swr'; + +interface Type { + useSWR: typeof useSWR, + useSWRInfinite: typeof useSWRInfinite, +} + +const Context = createContext({} as any) + +export const useFetchContext = (): Type => useContext(Context); +export const FetchContextProvider = ({ children }: { children: ComponentChildren }): VNode => { + return h(Context.Provider, { value: { useSWR, useSWRInfinite }, children }); +} + +export const FetchContextProviderTesting = ({ children, data }: { children: ComponentChildren, data:any }): VNode => { + return h(Context.Provider, { value: { useSWR: () => data, useSWRInfinite }, children }); +} diff --git a/packages/backend/src/context/instance.ts b/packages/backend/src/context/instance.ts new file mode 100644 index 0000000..fecf364 --- /dev/null +++ b/packages/backend/src/context/instance.ts @@ -0,0 +1,35 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { createContext } from 'preact' +import { useContext } from 'preact/hooks' + +interface Type { + id: string; + token?: string; + admin?: boolean; + changeToken: (t?:string) => void; +} + +const Context = createContext({} as any) + +export const InstanceContextProvider = Context.Provider +export const useInstanceContext = (): Type => useContext(Context); diff --git a/packages/backend/src/context/listener.ts b/packages/backend/src/context/listener.ts new file mode 100644 index 0000000..659db0a --- /dev/null +++ b/packages/backend/src/context/listener.ts @@ -0,0 +1,35 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { createContext } from 'preact' +import { useContext } from 'preact/hooks' + +interface Type { + id: string; + token?: string; + admin?: boolean; + changeToken: (t?:string) => void; +} + +const Context = createContext({} as any) + +export const ListenerContextProvider = Context.Provider +export const useListenerContext = (): Type => useContext(Context); diff --git a/packages/backend/src/context/translation.ts b/packages/backend/src/context/translation.ts new file mode 100644 index 0000000..952a1e3 --- /dev/null +++ b/packages/backend/src/context/translation.ts @@ -0,0 +1,59 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { createContext, h, VNode } from 'preact' +import { useContext, useEffect } from 'preact/hooks' +import { useLang } from '../hooks' +import * as jedLib from "jed"; +import { strings } from "../i18n/strings"; + +interface Type { + lang: string; + handler: any; + changeLanguage: (l: string) => void; +} +const initial = { + lang: 'en', + handler: null, + changeLanguage: () => { + // do not change anything + } +} +const Context = createContext(initial) + +interface Props { + initial?: string, + children: any, + forceLang?: string +} + +export const TranslationProvider = ({ initial, children, forceLang }: Props): VNode => { + const [lang, changeLanguage] = useLang(initial) + useEffect(() => { + if (forceLang) { + changeLanguage(forceLang) + } + }) + const handler = new jedLib.Jed(strings[lang]); + return h(Context.Provider, { value: { lang, handler, changeLanguage }, children }); +} + +export const useTranslationContext = (): Type => useContext(Context); \ No newline at end of file diff --git a/packages/backend/src/css/pure-min.css b/packages/backend/src/css/pure-min.css new file mode 100644 index 0000000..77217b5 --- /dev/null +++ b/packages/backend/src/css/pure-min.css @@ -0,0 +1,973 @@ +/*! + Pure v2.0.3 + Copyright 2013 Yahoo! + Licensed under the BSD License. + https://github.com/pure-cs s/pure/blob/master/LICENSE.md +*/ +/*! + normalize.cs s v | MIT License | git.io/normalize + Copyright (c) Nicolas Gallagher and Jonathan Neal +*/ +/*! normalize.cs s v8.0.1 | MIT License | github.com/necolas/normalize.cs s */ + +.talerbar { + text-align: center; +} + +html { + line-height: 1.15; + -webkit-text-size-adjust: 100%; +} +body { + margin: 0; +} +main { + display: block; +} +h1 { + font-size: 2em; + margin: 0.67em 0; +} +hr { + -webkit-box-sizing: content-box; + box-sizing: content-box; + height: 0; + overflow: visible; +} +pre { + font-family: monospace, monospace; + font-size: 1em; +} +a { + background-color: transparent; +} +abbr[title] { + border-bottom: none; + text-decoration: underline; + -webkit-text-decoration: underline dotted; + text-decoration: underline dotted; +} +b, +strong { + font-weight: bolder; +} +code, +kbd, +samp { + font-family: monospace, monospace; + font-size: 1em; +} +small { + font-size: 80%; +} +sub, +sup { + font-size: 75%; + line-height: 0; + position: relative; + vertical-align: baseline; +} +sub { + bottom: -0.25em; +} +sup { + top: -0.5em; +} +img { + border-style: none; +} +button, +input, +optgroup, +select, +textarea { + font-family: inherit; + font-size: 100%; + line-height: 1.15; + margin: 0; +} +button, +input { + overflow: visible; +} +button, +select { + text-transform: none; +} +[type="button"], +[type="reset"], +[type="submit"], +button { + -webkit-appearance: button; +} +[type="button"]::-moz-focus-inner, +[type="reset"]::-moz-focus-inner, +[type="submit"]::-moz-focus-inner, +button::-moz-focus-inner { + border-style: none; + padding: 0; +} +[type="button"]:-moz-focusring, +[type="reset"]:-moz-focusring, +[type="submit"]:-moz-focusring, +button:-moz-focusring { + outline: 1px dotted ButtonText; +} +fieldset { + padding: 0.35em 0.75em 0.625em; +} +legend { + -webkit-box-sizing: border-box; + box-sizing: border-box; + color: inherit; + display: table; + max-width: 100%; + padding: 0; + white-space: normal; +} +progress { + vertical-align: baseline; +} +textarea { + overflow: auto; +} +[type="checkbox"], +[type="radio"] { + -webkit-box-sizing: border-box; + box-sizing: border-box; + padding: 0; +} +[type="number"]::-webkit-inner-spin-button, +[type="number"]::-webkit-outer-spin-button { + height: auto; +} +[type="search"] { + -webkit-appearance: textfield; + outline-offset: -2px; +} +[type="search"]::-webkit-search-decoration { + -webkit-appearance: none; +} +::-webkit-file-upload-button { + -webkit-appearance: button; + font: inherit; +} +details { + display: block; +} +summary { + display: list-item; +} +template { + display: none; +} +[hidden] { + display: none; +} +html { + font-family: sans-serif; +} +.hidden, +[hidden] { + display: none !important; +} +.pure-img { + max-width: 100%; + height: auto; + display: block; +} +.pure-g { + letter-spacing: -0.31em; + text-rendering: optimizespeed; + font-family: FreeSans, Arimo, "Droid Sans", Helvetica, Arial, sans-serif; + display: -webkit-box; + display: -ms-flexbox; + display: flex; + -webkit-box-orient: horizontal; + -webkit-box-direction: normal; + -ms-flex-flow: row wrap; + flex-flow: row wrap; + -ms-flex-line-pack: start; + align-content: flex-start; +} +@media all and (-ms-high-contrast: none), (-ms-high-contrast: active) { + table .pure-g { + display: block; + } +} +.opera-only :-o-prefocus, +.pure-g { + word-spacing: -0.43em; +} +.pure-u { + display: inline-block; + letter-spacing: normal; + word-spacing: normal; + vertical-align: top; + text-rendering: auto; +} +.pure-g [class*="pure-u"] { + font-family: sans-serif; +} +.pure-u-1, +.pure-u-1-1, +.pure-u-1-12, +.pure-u-1-2, +.pure-u-1-24, +.pure-u-1-3, +.pure-u-1-4, +.pure-u-1-5, +.pure-u-1-6, +.pure-u-1-8, +.pure-u-10-24, +.pure-u-11-12, +.pure-u-11-24, +.pure-u-12-24, +.pure-u-13-24, +.pure-u-14-24, +.pure-u-15-24, +.pure-u-16-24, +.pure-u-17-24, +.pure-u-18-24, +.pure-u-19-24, +.pure-u-2-24, +.pure-u-2-3, +.pure-u-2-5, +.pure-u-20-24, +.pure-u-21-24, +.pure-u-22-24, +.pure-u-23-24, +.pure-u-24-24, +.pure-u-3-24, +.pure-u-3-4, +.pure-u-3-5, +.pure-u-3-8, +.pure-u-4-24, +.pure-u-4-5, +.pure-u-5-12, +.pure-u-5-24, +.pure-u-5-5, +.pure-u-5-6, +.pure-u-5-8, +.pure-u-6-24, +.pure-u-7-12, +.pure-u-7-24, +.pure-u-7-8, +.pure-u-8-24, +.pure-u-9-24 { + display: inline-block; + letter-spacing: normal; + word-spacing: normal; + vertical-align: top; + text-rendering: auto; +} +.pure-u-1-24 { + width: 4.1667%; +} +.pure-u-1-12, +.pure-u-2-24 { + width: 8.3333%; +} +.pure-u-1-8, +.pure-u-3-24 { + width: 12.5%; +} +.pure-u-1-6, +.pure-u-4-24 { + width: 16.6667%; +} +.pure-u-1-5 { + width: 20%; +} +.pure-u-5-24 { + width: 20.8333%; +} +.pure-u-1-4, +.pure-u-6-24 { + width: 25%; +} +.pure-u-7-24 { + width: 29.1667%; +} +.pure-u-1-3, +.pure-u-8-24 { + width: 33.3333%; +} +.pure-u-3-8, +.pure-u-9-24 { + width: 37.5%; +} +.pure-u-2-5 { + width: 40%; +} +.pure-u-10-24, +.pure-u-5-12 { + width: 41.6667%; +} +.pure-u-11-24 { + width: 45.8333%; +} +.pure-u-1-2, +.pure-u-12-24 { + width: 50%; +} +.pure-u-13-24 { + width: 54.1667%; +} +.pure-u-14-24, +.pure-u-7-12 { + width: 58.3333%; +} +.pure-u-3-5 { + width: 60%; +} +.pure-u-15-24, +.pure-u-5-8 { + width: 62.5%; +} +.pure-u-16-24, +.pure-u-2-3 { + width: 66.6667%; +} +.pure-u-17-24 { + width: 70.8333%; +} +.pure-u-18-24, +.pure-u-3-4 { + width: 75%; +} +.pure-u-19-24 { + width: 79.1667%; +} +.pure-u-4-5 { + width: 80%; +} +.pure-u-20-24, +.pure-u-5-6 { + width: 83.3333%; +} +.pure-u-21-24, +.pure-u-7-8 { + width: 87.5%; +} +.pure-u-11-12, +.pure-u-22-24 { + width: 91.6667%; +} +.pure-u-23-24 { + width: 95.8333%; +} +.pure-u-1, +.pure-u-1-1, +.pure-u-24-24, +.pure-u-5-5 { + width: 100%; +} +.pure-button { + display: inline-block; + line-height: normal; + white-space: nowrap; + vertical-align: middle; + text-align: center; + cursor: pointer; + -webkit-user-drag: none; + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; + -webkit-box-sizing: border-box; + box-sizing: border-box; +} +.pure-button::-moz-focus-inner { + padding: 0; + border: 0; +} +.pure-button-group { + letter-spacing: -0.31em; + text-rendering: optimizespeed; +} +.opera-only :-o-prefocus, +.pure-button-group { + word-spacing: -0.43em; +} +.pure-button-group .pure-button { + letter-spacing: normal; + word-spacing: normal; + vertical-align: top; + text-rendering: auto; +} +.pure-button { + font-family: inherit; + font-size: 100%; + padding: 0.5em 1em; + color: rgba(0, 0, 0, 0.8); + border: none transparent; + background-color: #e6e6e6; + text-decoration: none; + border-radius: 2px; +} +.pure-button-hover, +.pure-button:focus, +.pure-button:hover { + background-image: -webkit-gradient( + linear, + left top, + left bottom, + from(transparent), + color-stop(40%, rgba(0, 0, 0, 0.05)), + to(rgba(0, 0, 0, 0.1)) + ); + background-image: linear-gradient( + transparent, + rgba(0, 0, 0, 0.05) 40%, + rgba(0, 0, 0, 0.1) + ); +} +.pure-button:focus { + outline: 0; +} +.pure-button-active, +.pure-button:active { + -webkit-box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.15) inset, + 0 0 6px rgba(0, 0, 0, 0.2) inset; + box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.15) inset, + 0 0 6px rgba(0, 0, 0, 0.2) inset; + border-color: #000; +} +.pure-button-disabled, +.pure-button-disabled:active, +.pure-button-disabled:focus, +.pure-button-disabled:hover, +.pure-button[disabled] { + border: none; + background-image: none; + opacity: 0.4; + cursor: not-allowed; + -webkit-box-shadow: none; + box-shadow: none; + pointer-events: none; +} +.pure-button-hidden { + display: none; +} +.pure-button-primary, +.pure-button-selected, +a.pure-button-primary, +a.pure-button-selected { + background-color: #0078e7; + color: #fff; +} +.pure-button-group .pure-button { + margin: 0; + border-radius: 0; + border-right: 1px solid rgba(0, 0, 0, 0.2); +} +.pure-button-group .pure-button:first-child { + border-top-left-radius: 2px; + border-bottom-left-radius: 2px; +} +.pure-button-group .pure-button:last-child { + border-top-right-radius: 2px; + border-bottom-right-radius: 2px; + border-right: none; +} +.pure-form input[type="color"], +.pure-form input[type="date"], +.pure-form input[type="datetime-local"], +.pure-form input[type="datetime"], +.pure-form input[type="email"], +.pure-form input[type="month"], +.pure-form input[type="number"], +.pure-form input[type="password"], +.pure-form input[type="search"], +.pure-form input[type="tel"], +.pure-form input[type="text"], +.pure-form input[type="time"], +.pure-form input[type="url"], +.pure-form input[type="week"], +.pure-form select, +.pure-form textarea { + padding: 0.5em 0.6em; + display: inline-block; + border: 1px solid #ccc; + -webkit-box-shadow: inset 0 1px 3px #ddd; + box-shadow: inset 0 1px 3px #ddd; + border-radius: 4px; + vertical-align: middle; + -webkit-box-sizing: border-box; + box-sizing: border-box; +} +.pure-form input:not([type]) { + padding: 0.5em 0.6em; + display: inline-block; + border: 1px solid #ccc; + -webkit-box-shadow: inset 0 1px 3px #ddd; + box-shadow: inset 0 1px 3px #ddd; + border-radius: 4px; + -webkit-box-sizing: border-box; + box-sizing: border-box; +} +.pure-form input[type="color"] { + padding: 0.2em 0.5em; +} +.pure-form input[type="color"]:focus, +.pure-form input[type="date"]:focus, +.pure-form input[type="datetime-local"]:focus, +.pure-form input[type="datetime"]:focus, +.pure-form input[type="email"]:focus, +.pure-form input[type="month"]:focus, +.pure-form input[type="number"]:focus, +.pure-form input[type="password"]:focus, +.pure-form input[type="search"]:focus, +.pure-form input[type="tel"]:focus, +.pure-form input[type="text"]:focus, +.pure-form input[type="time"]:focus, +.pure-form input[type="url"]:focus, +.pure-form input[type="week"]:focus, +.pure-form select:focus, +.pure-form textarea:focus { + outline: 0; + border-color: #129fea; +} +.pure-form input:not([type]):focus { + outline: 0; + border-color: #129fea; +} +.pure-form input[type="checkbox"]:focus, +.pure-form input[type="file"]:focus, +.pure-form input[type="radio"]:focus { + outline: thin solid #129fea; + outline: 1px auto #129fea; +} +.pure-form .pure-checkbox, +.pure-form .pure-radio { + margin: 0.5em 0; + display: block; +} +.pure-form input[type="color"][disabled], +.pure-form input[type="date"][disabled], +.pure-form input[type="datetime-local"][disabled], +.pure-form input[type="datetime"][disabled], +.pure-form input[type="email"][disabled], +.pure-form input[type="month"][disabled], +.pure-form input[type="number"][disabled], +.pure-form input[type="password"][disabled], +.pure-form input[type="search"][disabled], +.pure-form input[type="tel"][disabled], +.pure-form input[type="text"][disabled], +.pure-form input[type="time"][disabled], +.pure-form input[type="url"][disabled], +.pure-form input[type="week"][disabled], +.pure-form select[disabled], +.pure-form textarea[disabled] { + cursor: not-allowed; + background-color: #eaeded; + color: #cad2d3; +} +.pure-form input:not([type])[disabled] { + cursor: not-allowed; + background-color: #eaeded; + color: #cad2d3; +} +.pure-form input[readonly], +.pure-form select[readonly], +.pure-form textarea[readonly] { + background-color: #eee; + color: #777; + border-color: #ccc; +} +.pure-form input:focus:invalid, +.pure-form select:focus:invalid, +.pure-form textarea:focus:invalid { + color: #b94a48; + border-color: #e9322d; +} +.pure-form input[type="checkbox"]:focus:invalid:focus, +.pure-form input[type="file"]:focus:invalid:focus, +.pure-form input[type="radio"]:focus:invalid:focus { + outline-color: #e9322d; +} +.pure-form select { + height: 2.25em; + border: 1px solid #ccc; + background-color: #fff; +} +.pure-form select[multiple] { + height: auto; +} +.pure-form label { + margin: 0.5em 0 0.2em; +} +.pure-form fieldset { + margin: 0; + padding: 0.35em 0 0.75em; + border: 0; +} +.pure-form legend { + display: block; + width: 100%; + padding: 0.3em 0; + margin-bottom: 0.3em; + color: #333; + border-bottom: 1px solid #e5e5e5; +} +.pure-form-stacked input[type="color"], +.pure-form-stacked input[type="date"], +.pure-form-stacked input[type="datetime-local"], +.pure-form-stacked input[type="datetime"], +.pure-form-stacked input[type="email"], +.pure-form-stacked input[type="file"], +.pure-form-stacked input[type="month"], +.pure-form-stacked input[type="number"], +.pure-form-stacked input[type="password"], +.pure-form-stacked input[type="search"], +.pure-form-stacked input[type="tel"], +.pure-form-stacked input[type="text"], +.pure-form-stacked input[type="time"], +.pure-form-stacked input[type="url"], +.pure-form-stacked input[type="week"], +.pure-form-stacked label, +.pure-form-stacked select, +.pure-form-stacked textarea { + display: block; + margin: 0.25em 0; +} +.pure-form-stacked input:not([type]) { + display: block; + margin: 0.25em 0; +} +.pure-form-aligned input, +.pure-form-aligned select, +.pure-form-aligned textarea, +.pure-form-message-inline { + display: inline-block; + vertical-align: middle; +} +.pure-form-aligned textarea { + vertical-align: top; +} +.pure-form-aligned .pure-control-group { + margin-bottom: 0.5em; +} +.pure-form-aligned .pure-control-group label { + text-align: right; + display: inline-block; + vertical-align: middle; + width: 10em; + margin: 0 1em 0 0; +} +.pure-form-aligned .pure-controls { + margin: 1.5em 0 0 11em; +} +.pure-form .pure-input-rounded, +.pure-form input.pure-input-rounded { + border-radius: 2em; + padding: 0.5em 1em; +} +.pure-form .pure-group fieldset { + margin-bottom: 10px; +} +.pure-form .pure-group input, +.pure-form .pure-group textarea { + display: block; + padding: 10px; + margin: 0 0 -1px; + border-radius: 0; + position: relative; + top: -1px; +} +.pure-form .pure-group input:focus, +.pure-form .pure-group textarea:focus { + z-index: 3; +} +.pure-form .pure-group input:first-child, +.pure-form .pure-group textarea:first-child { + top: 1px; + border-radius: 4px 4px 0 0; + margin: 0; +} +.pure-form .pure-group input:first-child:last-child, +.pure-form .pure-group textarea:first-child:last-child { + top: 1px; + border-radius: 4px; + margin: 0; +} +.pure-form .pure-group input:last-child, +.pure-form .pure-group textarea:last-child { + top: -2px; + border-radius: 0 0 4px 4px; + margin: 0; +} +.pure-form .pure-group button { + margin: 0.35em 0; +} +.pure-form .pure-input-1 { + width: 100%; +} +.pure-form .pure-input-3-4 { + width: 75%; +} +.pure-form .pure-input-2-3 { + width: 66%; +} +.pure-form .pure-input-1-2 { + width: 50%; +} +.pure-form .pure-input-1-3 { + width: 33%; +} +.pure-form .pure-input-1-4 { + width: 25%; +} +.pure-form-message-inline { + display: inline-block; + padding-left: 0.3em; + color: #666; + vertical-align: middle; + font-size: 0.875em; +} +.pure-form-message { + display: block; + color: #666; + font-size: 0.875em; +} +@media only screen and (max-width: 480px) { + .pure-form button[type="submit"] { + margin: 0.7em 0 0; + } + .pure-form input:not([type]), + .pure-form input[type="color"], + .pure-form input[type="date"], + .pure-form input[type="datetime-local"], + .pure-form input[type="datetime"], + .pure-form input[type="email"], + .pure-form input[type="month"], + .pure-form input[type="number"], + .pure-form input[type="password"], + .pure-form input[type="search"], + .pure-form input[type="tel"], + .pure-form input[type="text"], + .pure-form input[type="time"], + .pure-form input[type="url"], + .pure-form input[type="week"], + .pure-form label { + margin-bottom: 0.3em; + display: block; + } + .pure-group input:not([type]), + .pure-group input[type="color"], + .pure-group input[type="date"], + .pure-group input[type="datetime-local"], + .pure-group input[type="datetime"], + .pure-group input[type="email"], + .pure-group input[type="month"], + .pure-group input[type="number"], + .pure-group input[type="password"], + .pure-group input[type="search"], + .pure-group input[type="tel"], + .pure-group input[type="text"], + .pure-group input[type="time"], + .pure-group input[type="url"], + .pure-group input[type="week"] { + margin-bottom: 0; + } + .pure-form-aligned .pure-control-group label { + margin-bottom: 0.3em; + text-align: left; + display: block; + width: 100%; + } + .pure-form-aligned .pure-controls { + margin: 1.5em 0 0 0; + } + .pure-form-message, + .pure-form-message-inline { + display: block; + font-size: 0.75em; + padding: 0.2em 0 0.8em; + } +} +.pure-menu { + -webkit-box-sizing: border-box; + box-sizing: border-box; +} +.pure-menu-fixed { + position: fixed; + left: 0; + top: 0; + z-index: 3; +} +.pure-menu-item, +.pure-menu-list { + position: relative; +} +.pure-menu-list { + list-style: none; + margin: 0; + padding: 0; +} +.pure-menu-item { + padding: 0; + margin: 0; + height: 100%; +} +.pure-menu-heading, +.pure-menu-link { + display: block; + text-decoration: none; + white-space: nowrap; +} +.pure-menu-horizontal { + width: 100%; + white-space: nowrap; +} +.pure-menu-horizontal .pure-menu-list { + display: inline-block; +} +.pure-menu-horizontal .pure-menu-heading, +.pure-menu-horizontal .pure-menu-item, +.pure-menu-horizontal .pure-menu-separator { + display: inline-block; + vertical-align: middle; +} +.pure-menu-item .pure-menu-item { + display: block; +} +.pure-menu-children { + display: none; + position: absolute; + left: 100%; + top: 0; + margin: 0; + padding: 0; + z-index: 3; +} +.pure-menu-horizontal .pure-menu-children { + left: 0; + top: auto; + width: inherit; +} +.pure-menu-active > .pure-menu-children, +.pure-menu-allow-hover:hover > .pure-menu-children { + display: block; + position: absolute; +} +.pure-menu-has-children > .pure-menu-link:after { + padding-left: 0.5em; + content: "\25B8"; + font-size: small; +} +.pure-menu-horizontal .pure-menu-has-children > .pure-menu-link:after { + content: "\25BE"; +} +.pure-menu-scrollable { + overflow-y: scroll; + overflow-x: hidden; +} +.pure-menu-scrollable .pure-menu-list { + display: block; +} +.pure-menu-horizontal.pure-menu-scrollable .pure-menu-list { + display: inline-block; +} +.pure-menu-horizontal.pure-menu-scrollable { + white-space: nowrap; + overflow-y: hidden; + overflow-x: auto; + padding: 0.5em 0; +} +.pure-menu-horizontal .pure-menu-children .pure-menu-separator, +.pure-menu-separator { + background-color: #ccc; + height: 1px; + margin: 0.3em 0; +} +.pure-menu-horizontal .pure-menu-separator { + width: 1px; + height: 1.3em; + margin: 0 0.3em; +} +.pure-menu-horizontal .pure-menu-children .pure-menu-separator { + display: block; + width: auto; +} +.pure-menu-heading { + text-transform: uppercase; + color: #565d64; +} +.pure-menu-link { + color: #777; +} +.pure-menu-children { + background-color: #fff; +} +.pure-menu-disabled, +.pure-menu-heading, +.pure-menu-link { + padding: 0.5em 1em; +} +.pure-menu-disabled { + opacity: 0.5; +} +.pure-menu-disabled .pure-menu-link:hover { + background-color: transparent; +} +.pure-menu-active > .pure-menu-link, +.pure-menu-link:focus, +.pure-menu-link:hover { + background-color: #eee; +} +.pure-menu-selected > .pure-menu-link, +.pure-menu-selected > .pure-menu-link:visited { + color: #000; +} +.pure-table { + border-collapse: collapse; + border-spacing: 0; + empty-cells: show; + border: 1px solid #cbcbcb; +} +.pure-table caption { + color: #000; + font: italic 85%/1 arial, sans-serif; + padding: 1em 0; + text-align: center; +} +.pure-table td, +.pure-table th { + border-left: 1px solid #cbcbcb; + border-width: 0 0 0 1px; + font-size: inherit; + margin: 0; + overflow: visible; + padding: 0.5em 1em; +} +.pure-table thead { + background-color: #e0e0e0; + color: #000; + text-align: left; + vertical-align: bottom; +} +.pure-table td { + background-color: transparent; +} +.pure-table-odd td { + background-color: #f2f2f2; +} +.pure-table-striped tr:nth-child(2n-1) td { + background-color: #f2f2f2; +} +.pure-table-bordered td { + border-bottom: 1px solid #cbcbcb; +} +.pure-table-bordered tbody > tr:last-child > td { + border-bottom-width: 0; +} +.pure-table-horizontal td, +.pure-table-horizontal th { + border-width: 0 0 1px 0; + border-bottom: 1px solid #cbcbcb; +} +.pure-table-horizontal tbody > tr:last-child > td { + border-bottom-width: 0; +} diff --git a/packages/backend/src/css/style.css b/packages/backend/src/css/style.css new file mode 100644 index 0000000..e03b632 --- /dev/null +++ b/packages/backend/src/css/style.css @@ -0,0 +1,62 @@ +/*! + Pure v2.0.3 + Copyright 2013 Yahoo! + Licensed under the BSD License. + https://github.com/pure-ss/pure/blob/master/LICENSE.md +*/ +/*! + normalize.cs v | MIT License | git.io/normalize + Copyright (c) Nicolas Gallagher and Jonathan Neal +*/ +/*! normalize.ss v8.0.1 | MIT License | github.com/necolas/normalize.cs */ + +.talerbar { + text-align: center; +} +.tt { + font-family: "Lucida Console", Monaco, monospace; +} +.content { + overflow-x: auto; + padding-left: 15%; + padding-right: 15%; +} +.qr { + margin: auto; + text-align: center; +} +.qrtext { + width: max-content; + margin: auto; + transition: font-size 0.2s; + font-family: "Lucida Console", Monaco, monospace; + font-size: 0.5em; +} +.qrtext:hover { + font-size: 1em; +} +.talerbar { + margin: 0; + bottom: 0; + background-color: #033; + color: white; + width: 100%; + padding: 1em; + overflow: auto; +} +body { + overflow-y: scroll; +} +@media (min-width: 500px) { + .content { + padding-bottom: 2em; + margin-right: 1em; + overflow-y: auto; + } +} +#main a:link, +#main a:visited, +#main a:hover, +#main a:active { + color: black; +} \ No newline at end of file diff --git a/packages/backend/src/custom.d.ts b/packages/backend/src/custom.d.ts new file mode 100644 index 0000000..d270500 --- /dev/null +++ b/packages/backend/src/custom.d.ts @@ -0,0 +1,40 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ +declare module '*.po' { + const content: any; + export default content; +} +declare module 'jed' { + const x: any; + export = x; +} +declare module "*.jpeg" { + const content: any; + export default content; +} +declare module "*.png" { + const content: any; + export default content; +} +declare module '*.svg' { + const content: any; + export default content; +} + +declare module '*.scss' { + const content: Record; + export default content; +} diff --git a/packages/backend/src/declaration.d.ts b/packages/backend/src/declaration.d.ts new file mode 100644 index 0000000..1722a3d --- /dev/null +++ b/packages/backend/src/declaration.d.ts @@ -0,0 +1,1384 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + + +type HashCode = string; +type EddsaPublicKey = string; +type EddsaSignature = string; +type WireTransferIdentifierRawP = string; +type RelativeTime = Duration; +type ImageDataUrl = string; + +export interface WithId { + id: string +} + +interface Timestamp { + // Milliseconds since epoch, or the special + // value "forever" to represent an event that will + // never happen. + t_ms: number | "never"; +} +interface Duration { + // Duration in milliseconds or "forever" + // to represent an infinite duration. + d_ms: number | "forever"; +} + +interface WithId { + id: string; +} + +type Amount = string; +type UUID = string; +type Integer = number; + +export namespace ExchangeBackend { + interface WireResponse { + + // Master public key of the exchange, must match the key returned in /keys. + master_public_key: EddsaPublicKey; + + // Array of wire accounts operated by the exchange for + // incoming wire transfers. + accounts: WireAccount[]; + + // Object mapping names of wire methods (i.e. "sepa" or "x-taler-bank") + // to wire fees. + fees: { method: AggregateTransferFee }; + } + interface WireAccount { + // payto:// URI identifying the account and wire method + payto_uri: string; + + // Signature using the exchange's offline key + // with purpose TALER_SIGNATURE_MASTER_WIRE_DETAILS. + master_sig: EddsaSignature; + } + interface AggregateTransferFee { + // Per transfer wire transfer fee. + wire_fee: Amount; + + // Per transfer closing fee. + closing_fee: Amount; + + // What date (inclusive) does this fee go into effect? + // The different fees must cover the full time period in which + // any of the denomination keys are valid without overlap. + start_date: Timestamp; + + // What date (exclusive) does this fee stop going into effect? + // The different fees must cover the full time period in which + // any of the denomination keys are valid without overlap. + end_date: Timestamp; + + // Signature of TALER_MasterWireFeePS with + // purpose TALER_SIGNATURE_MASTER_WIRE_FEES. + sig: EddsaSignature; + } + +} +export namespace MerchantBackend { + interface ErrorDetail { + + // Numeric error code unique to the condition. + // The other arguments are specific to the error value reported here. + code: number; + + // Human-readable description of the error, i.e. "missing parameter", "commitment violation", ... + // Should give a human-readable hint about the error's nature. Optional, may change without notice! + hint?: string; + + // Optional detail about the specific input value that failed. May change without notice! + detail?: string; + + // Name of the parameter that was bogus (if applicable). + parameter?: string; + + // Path to the argument that was bogus (if applicable). + path?: string; + + // Offset of the argument that was bogus (if applicable). + offset?: string; + + // Index of the argument that was bogus (if applicable). + index?: string; + + // Name of the object that was bogus (if applicable). + object?: string; + + // Name of the currency than was problematic (if applicable). + currency?: string; + + // Expected type (if applicable). + type_expected?: string; + + // Type that was provided instead (if applicable). + type_actual?: string; + } + + + // Delivery location, loosely modeled as a subset of + // ISO20022's PostalAddress25. + interface Tax { + // the name of the tax + name: string; + + // amount paid in tax + tax: Amount; + } + + interface Auditor { + // official name + name: string; + + // Auditor's public key + auditor_pub: EddsaPublicKey; + + // Base URL of the auditor + url: string; + } + interface Exchange { + // the exchange's base URL + url: string; + + // master public key of the exchange + master_pub: EddsaPublicKey; + } + + interface Product { + // merchant-internal identifier for the product. + product_id?: string; + + // Human-readable product description. + description: string; + + // Map from IETF BCP 47 language tags to localized descriptions + description_i18n?: { [lang_tag: string]: string }; + + // The number of units of the product to deliver to the customer. + quantity: Integer; + + // The unit in which the product is measured (liters, kilograms, packages, etc.) + unit: string; + + // The price of the product; this is the total price for quantity times unit of this product. + price: Amount; + + // An optional base64-encoded product image + image: ImageDataUrl; + + // a list of taxes paid by the merchant for this product. Can be empty. + taxes: Tax[]; + + // time indicating when this product should be delivered + delivery_date?: Timestamp; + } + interface Merchant { + // label for a location with the business address of the merchant + address: Location; + + // the merchant's legal name of business + name: string; + + // label for a location that denotes the jurisdiction for disputes. + // Some of the typical fields for a location (such as a street address) may be absent. + jurisdiction: Location; + } + + interface VersionResponse { + // libtool-style representation of the Merchant protocol version, see + // https://www.gnu.org/software/libtool/manual/html_node/Versioning.html#Versioning + // The format is "current:revision:age". + version: string; + + // Name of the protocol. + name: "taler-merchant"; + + // Currency supported by this backend. + currency: string; + + } + interface Location { + // Nation with its own government. + country?: string; + + // Identifies a subdivision of a country such as state, region, county. + country_subdivision?: string; + + // Identifies a subdivision within a country sub-division. + district?: string; + + // Name of a built-up area, with defined boundaries, and a local government. + town?: string; + + // Specific location name within the town. + town_location?: string; + + // Identifier consisting of a group of letters and/or numbers that + // is added to a postal address to assist the sorting of mail. + post_code?: string; + + // Name of a street or thoroughfare. + street?: string; + + // Name of the building or house. + building_name?: string; + + // Number that identifies the position of a building on a street. + building_number?: string; + + // Free-form address lines, should not exceed 7 elements. + address_lines?: string[]; + } + namespace Instances { + + //POST /private/instances/$INSTANCE/auth + interface InstanceAuthConfigurationMessage { + // Type of authentication. + // "external": The mechant backend does not do + // any authentication checks. Instead an API + // gateway must do the authentication. + // "token": The merchant checks an auth token. + // See "token" for details. + method: "external" | "token"; + + // For method "external", this field is mandatory. + // The token MUST begin with the string "secret-token:". + // After the auth token has been set (with method "token"), + // the value must be provided in a "Authorization: Bearer $token" + // header. + token?: string; + + } + //POST /private/instances + interface InstanceConfigurationMessage { + // The URI where the wallet will send coins. A merchant may have + // multiple accounts, thus this is an array. Note that by + // removing URIs from this list the respective account is set to + // inactive and thus unavailable for new contracts, but preserved + // in the database as existing offers and contracts may still refer + // to it. + payto_uris: string[]; + + // Name of the merchant instance to create (will become $INSTANCE). + id: string; + + // Merchant name corresponding to this instance. + name: string; + + // "Authentication" header required to authorize management access the instance. + // Optional, if not given authentication will be disabled for + // this instance (hopefully authentication checks are still + // done by some reverse proxy). + auth: InstanceAuthConfigurationMessage; + + // The merchant's physical address (to be put into contracts). + address: Location; + + // The jurisdiction under which the merchant conducts its business + // (to be put into contracts). + jurisdiction: Location; + + // Maximum wire fee this instance is willing to pay. + // Can be overridden by the frontend on a per-order basis. + default_max_wire_fee: Amount; + + // Default factor for wire fee amortization calculations. + // Can be overridden by the frontend on a per-order basis. + default_wire_fee_amortization: Integer; + + // Maximum deposit fee (sum over all coins) this instance is willing to pay. + // Can be overridden by the frontend on a per-order basis. + default_max_deposit_fee: Amount; + + // If the frontend does NOT specify an execution date, how long should + // we tell the exchange to wait to aggregate transactions before + // executing the wire transfer? This delay is added to the current + // time when we generate the advisory execution time for the exchange. + default_wire_transfer_delay: RelativeTime; + + // If the frontend does NOT specify a payment deadline, how long should + // offers we make be valid by default? + default_pay_delay: RelativeTime; + + } + + // PATCH /private/instances/$INSTANCE + interface InstanceReconfigurationMessage { + // The URI where the wallet will send coins. A merchant may have + // multiple accounts, thus this is an array. Note that by + // removing URIs from this list + payto_uris: string[]; + + // Merchant name corresponding to this instance. + name: string; + + // The merchant's physical address (to be put into contracts). + address: Location; + + // The jurisdiction under which the merchant conducts its business + // (to be put into contracts). + jurisdiction: Location; + + // Maximum wire fee this instance is willing to pay. + // Can be overridden by the frontend on a per-order basis. + default_max_wire_fee: Amount; + + // Default factor for wire fee amortization calculations. + // Can be overridden by the frontend on a per-order basis. + default_wire_fee_amortization: Integer; + + // Maximum deposit fee (sum over all coins) this instance is willing to pay. + // Can be overridden by the frontend on a per-order basis. + default_max_deposit_fee: Amount; + + // If the frontend does NOT specify an execution date, how long should + // we tell the exchange to wait to aggregate transactions before + // executing the wire transfer? This delay is added to the current + // time when we generate the advisory execution time for the exchange. + default_wire_transfer_delay: RelativeTime; + + // If the frontend does NOT specify a payment deadline, how long should + // offers we make be valid by default? + default_pay_delay: RelativeTime; + + } + + // GET /private/instances + interface InstancesResponse { + // List of instances that are present in the backend (see Instance) + instances: Instance[]; + } + + interface Instance { + // Merchant name corresponding to this instance. + name: string; + + deleted?: boolean; + + // Merchant instance this response is about ($INSTANCE) + id: string; + + // Public key of the merchant/instance, in Crockford Base32 encoding. + merchant_pub: EddsaPublicKey; + + // List of the payment targets supported by this instance. Clients can + // specify the desired payment target in /order requests. Note that + // front-ends do not have to support wallets selecting payment targets. + payment_targets: string[]; + + } + + //GET /private/instances/$INSTANCE + interface QueryInstancesResponse { + // The URI where the wallet will send coins. A merchant may have + // multiple accounts, thus this is an array. + accounts: MerchantAccount[]; + + // Merchant name corresponding to this instance. + name: string; + + // Public key of the merchant/instance, in Crockford Base32 encoding. + merchant_pub: EddsaPublicKey; + + // The merchant's physical address (to be put into contracts). + address: Location; + + // The jurisdiction under which the merchant conducts its business + // (to be put into contracts). + jurisdiction: Location; + + // Maximum wire fee this instance is willing to pay. + // Can be overridden by the frontend on a per-order basis. + default_max_wire_fee: Amount; + + // Default factor for wire fee amortization calculations. + // Can be overridden by the frontend on a per-order basis. + default_wire_fee_amortization: Integer; + + // Maximum deposit fee (sum over all coins) this instance is willing to pay. + // Can be overridden by the frontend on a per-order basis. + default_max_deposit_fee: Amount; + + // If the frontend does NOT specify an execution date, how long should + // we tell the exchange to wait to aggregate transactions before + // executing the wire transfer? This delay is added to the current + // time when we generate the advisory execution time for the exchange. + default_wire_transfer_delay: RelativeTime; + + // If the frontend does NOT specify a payment deadline, how long should + // offers we make be valid by default? + default_pay_delay: RelativeTime; + + // Authentication configuration. + // Does not contain the token when token auth is configured. + auth: { + method: "external" | "token"; + }; + } + + interface MerchantAccount { + + // payto:// URI of the account. + payto_uri: string; + + // Hash over the wire details (including over the salt) + h_wire: HashCode; + + // salt used to compute h_wire + salt: HashCode; + + // true if this account is active, + // false if it is historic. + active: boolean; + } + + // DELETE /private/instances/$INSTANCE + + + } + + namespace Products { + // POST /private/products + interface ProductAddDetail { + + // product ID to use. + product_id: string; + + // Human-readable product description. + description: string; + + // Map from IETF BCP 47 language tags to localized descriptions + description_i18n: { [lang_tag: string]: string }; + + // unit in which the product is measured (liters, kilograms, packages, etc.) + unit: string; + + // The price for one unit of the product. Zero is used + // to imply that this product is not sold separately, or + // that the price is not fixed, and must be supplied by the + // front-end. If non-zero, this price MUST include applicable + // taxes. + price: Amount; + + // An optional base64-encoded product image + image: ImageDataUrl; + + // a list of taxes paid by the merchant for one unit of this product + taxes: Tax[]; + + // Number of units of the product in stock in sum in total, + // including all existing sales ever. Given in product-specific + // units. + // A value of -1 indicates "infinite" (i.e. for "electronic" books). + total_stock: Integer; + + // Identifies where the product is in stock. + address: Location; + + // Identifies when we expect the next restocking to happen. + next_restock?: Timestamp; + + } + // PATCH /private/products/$PRODUCT_ID + interface ProductPatchDetail { + + // Human-readable product description. + description: string; + + // Map from IETF BCP 47 language tags to localized descriptions + description_i18n: { [lang_tag: string]: string }; + + // unit in which the product is measured (liters, kilograms, packages, etc.) + unit: string; + + // The price for one unit of the product. Zero is used + // to imply that this product is not sold separately, or + // that the price is not fixed, and must be supplied by the + // front-end. If non-zero, this price MUST include applicable + // taxes. + price: Amount; + + // An optional base64-encoded product image + image: ImageDataUrl; + + // a list of taxes paid by the merchant for one unit of this product + taxes: Tax[]; + + // Number of units of the product in stock in sum in total, + // including all existing sales ever. Given in product-specific + // units. + // A value of -1 indicates "infinite" (i.e. for "electronic" books). + total_stock: Integer; + + // Number of units of the product that were lost (spoiled, stolen, etc.) + total_lost: Integer; + + // Identifies where the product is in stock. + address: Location; + + // Identifies when we expect the next restocking to happen. + next_restock?: Timestamp; + + } + + // GET /private/products + interface InventorySummaryResponse { + // List of products that are present in the inventory + products: InventoryEntry[]; + } + interface InventoryEntry { + // Product identifier, as found in the product. + product_id: string; + + } + + // GET /private/products/$PRODUCT_ID + interface ProductDetail { + + // Human-readable product description. + description: string; + + // Map from IETF BCP 47 language tags to localized descriptions + description_i18n: { [lang_tag: string]: string }; + + // unit in which the product is measured (liters, kilograms, packages, etc.) + unit: string; + + // The price for one unit of the product. Zero is used + // to imply that this product is not sold separately, or + // that the price is not fixed, and must be supplied by the + // front-end. If non-zero, this price MUST include applicable + // taxes. + price: Amount; + + // An optional base64-encoded product image + image: ImageDataUrl; + + // a list of taxes paid by the merchant for one unit of this product + taxes: Tax[]; + + // Number of units of the product in stock in sum in total, + // including all existing sales ever. Given in product-specific + // units. + // A value of -1 indicates "infinite" (i.e. for "electronic" books). + total_stock: Integer; + + // Number of units of the product that have already been sold. + total_sold: Integer; + + // Number of units of the product that were lost (spoiled, stolen, etc.) + total_lost: Integer; + + // Identifies where the product is in stock. + address: Location; + + // Identifies when we expect the next restocking to happen. + next_restock?: Timestamp; + + } + + // POST /private/products/$PRODUCT_ID/lock + interface LockRequest { + + // UUID that identifies the frontend performing the lock + // It is suggested that clients use a timeflake for this, + // see https://github.com/anthonynsimon/timeflake + lock_uuid: UUID; + + // How long does the frontend intend to hold the lock + duration: RelativeTime; + + // How many units should be locked? + quantity: Integer; + + } + + // DELETE /private/products/$PRODUCT_ID + + } + + namespace Orders { + + type MerchantOrderStatusResponse = CheckPaymentPaidResponse | + CheckPaymentClaimedResponse | + CheckPaymentUnpaidResponse; + interface CheckPaymentPaidResponse { + // The customer paid for this contract. + order_status: "paid"; + + // Was the payment refunded (even partially)? + refunded: boolean; + + // True if there are any approved refunds that the wallet has + // not yet obtained. + refund_pending: boolean; + + // Did the exchange wire us the funds? + wired: boolean; + + // Total amount the exchange deposited into our bank account + // for this contract, excluding fees. + deposit_total: Amount; + + // Numeric error code indicating errors the exchange + // encountered tracking the wire transfer for this purchase (before + // we even got to specific coin issues). + // 0 if there were no issues. + exchange_ec: number; + + // HTTP status code returned by the exchange when we asked for + // information to track the wire transfer for this purchase. + // 0 if there were no issues. + exchange_hc: number; + + // Total amount that was refunded, 0 if refunded is false. + refund_amount: Amount; + + // Contract terms. + contract_terms: ContractTerms; + + // The wire transfer status from the exchange for this order if + // available, otherwise empty array. + wire_details: TransactionWireTransfer[]; + + // Reports about trouble obtaining wire transfer details, + // empty array if no trouble were encountered. + wire_reports: TransactionWireReport[]; + + // The refund details for this order. One entry per + // refunded coin; empty array if there are no refunds. + refund_details: RefundDetails[]; + + // Status URL, can be used as a redirect target for the browser + // to show the order QR code / trigger the wallet. + order_status_url: string; + } + interface CheckPaymentClaimedResponse { + // A wallet claimed the order, but did not yet pay for the contract. + order_status: "claimed"; + + // Contract terms. + contract_terms: ContractTerms; + + } + interface CheckPaymentUnpaidResponse { + // The order was neither claimed nor paid. + order_status: "unpaid"; + + // when was the order created + creation_time: Timestamp; + + // Order summary text. + summary: string; + + // Total amount of the order (to be paid by the customer). + total_amount: Amount; + + // URI that the wallet must process to complete the payment. + taler_pay_uri: string; + + // Alternative order ID which was paid for already in the same session. + // Only given if the same product was purchased before in the same session. + already_paid_order_id?: string; + + // Fulfillment URL of an already paid order. Only given if under this + // session an already paid order with a fulfillment URL exists. + already_paid_fulfillment_url?: string; + + // Status URL, can be used as a redirect target for the browser + // to show the order QR code / trigger the wallet. + order_status_url: string; + + // We do we NOT return the contract terms here because they may not + // exist in case the wallet did not yet claim them. + } + interface RefundDetails { + // Reason given for the refund. + reason: string; + + // When was the refund approved. + timestamp: Timestamp; + + // Total amount that was refunded (minus a refund fee). + amount: Amount; + } + interface TransactionWireTransfer { + // Responsible exchange. + exchange_url: string; + + // 32-byte wire transfer identifier. + wtid: Base32; + + // Execution time of the wire transfer. + execution_time: Timestamp; + + // Total amount that has been wire transferred + // to the merchant. + amount: Amount; + + // Was this transfer confirmed by the merchant via the + // POST /transfers API, or is it merely claimed by the exchange? + confirmed: boolean; + } + interface TransactionWireReport { + // Numerical error code. + code: number; + + // Human-readable error description. + hint: string; + + // Numerical error code from the exchange. + exchange_ec: number; + + // HTTP status code received from the exchange. + exchange_hc: number; + + // Public key of the coin for which we got the exchange error. + coin_pub: CoinPublicKey; + } + + interface OrderHistory { + // timestamp-sorted array of all orders matching the query. + // The order of the sorting depends on the sign of delta. + orders: OrderHistoryEntry[]; + } + interface OrderHistoryEntry { + + // order ID of the transaction related to this entry. + order_id: string; + + // row ID of the order in the database + row_id: number; + + // when the order was created + timestamp: Timestamp; + + // the amount of money the order is for + amount: Amount; + + // the summary of the order + summary: string; + + // whether some part of the order is refundable, + // that is the refund deadline has not yet expired + // and the total amount refunded so far is below + // the value of the original transaction. + refundable: boolean; + + // whether the order has been paid or not + paid: boolean; + } + + interface PostOrderRequest { + // The order must at least contain the minimal + // order detail, but can override all + order: Order; + + // if set, the backend will then set the refund deadline to the current + // time plus the specified delay. If it's not set, refunds will not be + // possible. + refund_delay?: RelativeTime; + + // specifies the payment target preferred by the client. Can be used + // to select among the various (active) wire methods supported by the instance. + payment_target?: string; + + // specifies that some products are to be included in the + // order from the inventory. For these inventory management + // is performed (so the products must be in stock) and + // details are completed from the product data of the backend. + inventory_products?: MinimalInventoryProduct[]; + + // Specifies a lock identifier that was used to + // lock a product in the inventory. Only useful if + // manage_inventory is set. Used in case a frontend + // reserved quantities of the individual products while + // the shopping card was being built. Multiple UUIDs can + // be used in case different UUIDs were used for different + // products (i.e. in case the user started with multiple + // shopping sessions that were combined during checkout). + lock_uuids?: UUID[]; + + // Should a token for claiming the order be generated? + // False can make sense if the ORDER_ID is sufficiently + // high entropy to prevent adversarial claims (like it is + // if the backend auto-generates one). Default is 'true'. + create_token?: boolean; + + } + type Order = MinimalOrderDetail | ContractTerms; + + interface MinimalOrderDetail { + // Amount to be paid by the customer + amount: Amount; + + // Short summary of the order + summary: string; + + // URL that will show that the order was successful after + // it has been paid for. Optional. When POSTing to the + // merchant, the placeholder "${ORDER_ID}" will be + // replaced with the actual order ID (useful if the + // order ID is generated server-side and needs to be + // in the URL). + fulfillment_url?: string; + } + + interface MinimalInventoryProduct { + // Which product is requested (here mandatory!) + product_id: string; + + // How many units of the product are requested + quantity: Integer; + } + interface PostOrderResponse { + // Order ID of the response that was just created + order_id: string; + + // Token that authorizes the wallet to claim the order. + // Provided only if "create_token" was set to 'true' + // in the request. + token?: ClaimToken; + } + interface OutOfStockResponse { + + // Product ID of an out-of-stock item + product_id: string; + + // Requested quantity + requested_quantity: Integer; + + // Available quantity (must be below requested_quanitity) + available_quantity: Integer; + + // When do we expect the product to be again in stock? + // Optional, not given if unknown. + restock_expected?: Timestamp; + } + + interface ForgetRequest { + + // Array of valid JSON paths to forgettable fields in the order's + // contract terms. + fields: string[]; + } + interface RefundRequest { + // Amount to be refunded + refund: Amount; + + // Human-readable refund justification + reason: string; + } + interface MerchantRefundResponse { + + // URL (handled by the backend) that the wallet should access to + // trigger refund processing. + // taler://refund/... + taler_refund_uri: string; + + // Contract hash that a client may need to authenticate an + // HTTP request to obtain the above URI in a wallet-friendly way. + h_contract: HashCode; + } + + } + + namespace Tips { + + // GET /private/reserves + interface TippingReserveStatus { + // Array of all known reserves (possibly empty!) + reserves: ReserveStatusEntry[]; + } + interface ReserveStatusEntry { + // Public key of the reserve + reserve_pub: EddsaPublicKey; + + // Timestamp when it was established + creation_time: Timestamp; + + // Timestamp when it expires + expiration_time: Timestamp; + + // Initial amount as per reserve creation call + merchant_initial_amount: Amount; + + // Initial amount as per exchange, 0 if exchange did + // not confirm reserve creation yet. + exchange_initial_amount: Amount; + + // Amount picked up so far. + pickup_amount: Amount; + + // Amount approved for tips that exceeds the pickup_amount. + committed_amount: Amount; + + // Is this reserve active (false if it was deleted but not purged) + active: boolean; + } + + interface ReserveCreateRequest { + // Amount that the merchant promises to put into the reserve + initial_balance: Amount; + + // Exchange the merchant intends to use for tipping + exchange_url: string; + + // Desired wire method, for example "iban" or "x-taler-bank" + wire_method: string; + } + interface ReserveCreateConfirmation { + // Public key identifying the reserve + reserve_pub: EddsaPublicKey; + + // Wire account of the exchange where to transfer the funds + payto_uri: string; + } + interface TipCreateRequest { + // Amount that the customer should be tipped + amount: Amount; + + // Justification for giving the tip + justification: string; + + // URL that the user should be directed to after tipping, + // will be included in the tip_token. + next_url: string; + } + interface TipCreateConfirmation { + // Unique tip identifier for the tip that was created. + tip_id: HashCode; + + // taler://tip URI for the tip + taler_tip_uri: string; + + // URL that will directly trigger processing + // the tip when the browser is redirected to it + tip_status_url: string; + + // when does the tip expire + tip_expiration: Timestamp; + } + + interface ReserveDetail { + // Timestamp when it was established. + creation_time: Timestamp; + + // Timestamp when it expires. + expiration_time: Timestamp; + + // Initial amount as per reserve creation call. + merchant_initial_amount: Amount; + + // Initial amount as per exchange, 0 if exchange did + // not confirm reserve creation yet. + exchange_initial_amount: Amount; + + // Amount picked up so far. + pickup_amount: Amount; + + // Amount approved for tips that exceeds the pickup_amount. + committed_amount: Amount; + + // Array of all tips created by this reserves (possibly empty!). + // Only present if asked for explicitly. + tips?: TipStatusEntry[]; + + // Is this reserve active (false if it was deleted but not purged)? + active: boolean; + + // URI to use to fill the reserve, can be NULL + // if the reserve is inactive or was already filled + payto_uri: string; + + // URL of the exchange hosting the reserve, + // NULL if the reserve is inactive + exchange_url: string; + + } + + interface TipStatusEntry { + + // Unique identifier for the tip. + tip_id: HashCode; + + // Total amount of the tip that can be withdrawn. + total_amount: Amount; + + // Human-readable reason for why the tip was granted. + reason: string; + } + + interface TipDetails { + // Amount that we authorized for this tip. + total_authorized: Amount; + + // Amount that was picked up by the user already. + total_picked_up: Amount; + + // Human-readable reason given when authorizing the tip. + reason: string; + + // Timestamp indicating when the tip is set to expire (may be in the past). + expiration: Timestamp; + + // Reserve public key from which the tip is funded. + reserve_pub: EddsaPublicKey; + + // Array showing the pickup operations of the wallet (possibly empty!). + // Only present if asked for explicitly. + pickups?: PickupDetail[]; + } + interface PickupDetail { + // Unique identifier for the pickup operation. + pickup_id: HashCode; + + // Number of planchets involved. + num_planchets: Integer; + + // Total amount requested for this pickup_id. + requested_amount: Amount; + } + + } + + namespace Transfers { + + interface TransferList { + // list of all the transfers that fit the filter that we know + transfers: TransferDetails[]; + } + interface TransferDetails { + // how much was wired to the merchant (minus fees) + credit_amount: Amount; + + // raw wire transfer identifier identifying the wire transfer (a base32-encoded value) + wtid: string; + + // target account that received the wire transfer + payto_uri: string; + + // base URL of the exchange that made the wire transfer + exchange_url: string; + + // Serial number identifying the transfer in the merchant backend. + // Used for filgering via offset. + transfer_serial_id: number; + + // Time of the execution of the wire transfer by the exchange, according to the exchange + // Only provided if we did get an answer from the exchange. + execution_time?: Timestamp; + + // True if we checked the exchange's answer and are happy with it. + // False if we have an answer and are unhappy, missing if we + // do not have an answer from the exchange. + verified?: boolean; + + // True if the merchant uses the POST /transfers API to confirm + // that this wire transfer took place (and it is thus not + // something merely claimed by the exchange). + confirmed?: boolean; + } + + interface TransferInformation { + // how much was wired to the merchant (minus fees) + credit_amount: Amount; + + // raw wire transfer identifier identifying the wire transfer (a base32-encoded value) + wtid: WireTransferIdentifierRawP; + + // target account that received the wire transfer + payto_uri: string; + + // base URL of the exchange that made the wire transfer + exchange_url: string; + } + interface MerchantTrackTransferResponse { + // Total amount transferred + total: Amount; + + // Applicable wire fee that was charged + wire_fee: Amount; + + // Time of the execution of the wire transfer by the exchange, according to the exchange + execution_time: Timestamp; + + // details about the deposits + deposits_sums: MerchantTrackTransferDetail[]; + } + interface MerchantTrackTransferDetail { + // Business activity associated with the wire transferred amount + // deposit_value. + order_id: string; + + // The total amount the exchange paid back for order_id. + deposit_value: Amount; + + // applicable fees for the deposit + deposit_fee: Amount; + } + + type ExchangeConflictDetails = WireFeeConflictDetails | TrackTransferConflictDetails + // Note: this is not the full 'proof' of missbehavior, as + // the bogus message from the exchange with a signature + // over the 'different' wire fee is missing. + // + // This information is NOT provided by the current implementation, + // because this would be quite expensive to generate and is + // hardly needed _here_. Once we add automated reports for + // the Taler auditor, we need to generate this data anyway + // and should probably return it here as well. + interface WireFeeConflictDetails { + // Numerical error code: + code: "TALER_EC_MERCHANT_PRIVATE_POST_TRANSFERS_BAD_WIRE_FEE"; + + // Text describing the issue for humans. + hint: string; + + + // Wire fee (wrongly) charged by the exchange, breaking the + // contract affirmed by the exchange_sig. + wire_fee: Amount; + + // Timestamp of the wire transfer + execution_time: Timestamp; + + // The expected wire fee (as signed by the exchange) + expected_wire_fee: Amount; + + // Expected closing fee (needed to verify signature) + expected_closing_fee: Amount; + + // Start date of the expected fee structure + start_date: Timestamp; + + // End date of the expected fee structure + end_date: Timestamp; + + // Signature of the exchange affirming the expected fee structure + master_sig: EddsaSignature; + + // Master public key of the exchange + master_pub: EddsaPublicKey; + } + interface TrackTransferConflictDetails { + // Numerical error code + code: "TALER_EC_MERCHANT_PRIVATE_POST_TRANSFERS_CONFLICTING_REPORTS"; + + // Text describing the issue for humans. + hint: string; + + // Offset in the exchange_transfer where the + // exchange's response fails to match the exchange_deposit_proof. + conflict_offset: number; + + // The response from the exchange which tells us when the + // coin was returned to us, except that it does not match + // the expected value of the coin. + // + // This field is NOT provided by the current implementation, + // because this would be quite expensive to generate and is + // hardly needed _here_. Once we add automated reports for + // the Taler auditor, we need to generate this data anyway + // and should probably return it here as well. + // exchange_transfer?: TrackTransferResponse; + + // Public key of the exchange used to sign the response to + // our deposit request. + deposit_exchange_pub: EddsaPublicKey; + + // Signature of the exchange signing the (conflicting) response. + // Signs over a struct TALER_DepositConfirmationPS. + deposit_exchange_sig: EddsaSignature; + + // Hash of the merchant's bank account the wire transfer went to + h_wire: HashCode; + + // Hash of the contract terms with the conflicting deposit. + h_contract_terms: HashCode; + + // At what time the exchange received the deposit. Needed + // to verify the \exchange_sig\. + deposit_timestamp: Timestamp; + + // At what time the refund possibility expired (needed to verify exchange_sig). + refund_deadline: Timestamp; + + // Public key of the coin for which we have conflicting information. + coin_pub: EddsaPublicKey; + + // Amount the exchange counted the coin for in the transfer. + amount_with_fee: Amount; + + // Expected value of the coin. + coin_value: Amount; + + // Expected deposit fee of the coin. + coin_fee: Amount; + + // Expected deposit fee of the coin. + deposit_fee: Amount; + + } + + // interface TrackTransferProof { + // // signature from the exchange made with purpose + // // TALER_SIGNATURE_EXCHANGE_CONFIRM_WIRE_DEPOSIT + // exchange_sig: EddsaSignature; + + // // public EdDSA key of the exchange that was used to generate the signature. + // // Should match one of the exchange's signing keys from /keys. Again given + // // explicitly as the client might otherwise be confused by clock skew as to + // // which signing key was used. + // exchange_pub: EddsaSignature; + + // // hash of the wire details (identical for all deposits) + // // Needed to check the exchange_sig + // h_wire: HashCode; + // } + + } + + + interface ContractTerms { + // Human-readable description of the whole purchase + summary: string; + + // Map from IETF BCP 47 language tags to localized summaries + summary_i18n?: { [lang_tag: string]: string }; + + // Unique, free-form identifier for the proposal. + // Must be unique within a merchant instance. + // For merchants that do not store proposals in their DB + // before the customer paid for them, the order_id can be used + // by the frontend to restore a proposal from the information + // encoded in it (such as a short product identifier and timestamp). + order_id: string; + + // Total price for the transaction. + // The exchange will subtract deposit fees from that amount + // before transferring it to the merchant. + amount: Amount; + + // The URL for this purchase. Every time is is visited, the merchant + // will send back to the customer the same proposal. Clearly, this URL + // can be bookmarked and shared by users. + fulfillment_url?: string; + + // Maximum total deposit fee accepted by the merchant for this contract + max_fee: Amount; + + // Maximum wire fee accepted by the merchant (customer share to be + // divided by the 'wire_fee_amortization' factor, and further reduced + // if deposit fees are below 'max_fee'). Default if missing is zero. + max_wire_fee: Amount; + + // Over how many customer transactions does the merchant expect to + // amortize wire fees on average? If the exchange's wire fee is + // above 'max_wire_fee', the difference is divided by this number + // to compute the expected customer's contribution to the wire fee. + // The customer's contribution may further be reduced by the difference + // between the 'max_fee' and the sum of the actual deposit fees. + // Optional, default value if missing is 1. 0 and negative values are + // invalid and also interpreted as 1. + wire_fee_amortization: number; + + // List of products that are part of the purchase (see Product). + products: Product[]; + + // Time when this contract was generated + timestamp: Timestamp; + + // After this deadline has passed, no refunds will be accepted. + refund_deadline: Timestamp; + + // After this deadline, the merchant won't accept payments for the contact + pay_deadline: Timestamp; + + // Transfer deadline for the exchange. Must be in the + // deposit permissions of coins used to pay for this order. + wire_transfer_deadline: Timestamp; + + // Merchant's public key used to sign this proposal; this information + // is typically added by the backend Note that this can be an ephemeral key. + merchant_pub: EddsaPublicKey; + + // Base URL of the (public!) merchant backend API. + // Must be an absolute URL that ends with a slash. + merchant_base_url: string; + + // More info about the merchant, see below + merchant: Merchant; + + // The hash of the merchant instance's wire details. + h_wire: HashCode; + + // Wire transfer method identifier for the wire method associated with h_wire. + // The wallet may only select exchanges via a matching auditor if the + // exchange also supports this wire method. + // The wire transfer fees must be added based on this wire transfer method. + wire_method: string; + + // Any exchanges audited by these auditors are accepted by the merchant. + auditors: Auditor[]; + + // Exchanges that the merchant accepts even if it does not accept any auditors that audit them. + exchanges: Exchange[]; + + // Delivery location for (all!) products. + delivery_location?: Location; + + // Time indicating when the order should be delivered. + // May be overwritten by individual products. + delivery_date?: Timestamp; + + // Nonce generated by the wallet and echoed by the merchant + // in this field when the proposal is generated. + nonce: string; + + // Specifies for how long the wallet should try to get an + // automatic refund for the purchase. If this field is + // present, the wallet should wait for a few seconds after + // the purchase and then automatically attempt to obtain + // a refund. The wallet should probe until "delay" + // after the payment was successful (i.e. via long polling + // or via explicit requests with exponential back-off). + // + // In particular, if the wallet is offline + // at that time, it MUST repeat the request until it gets + // one response from the merchant after the delay has expired. + // If the refund is granted, the wallet MUST automatically + // recover the payment. This is used in case a merchant + // knows that it might be unable to satisfy the contract and + // desires for the wallet to attempt to get the refund without any + // customer interaction. Note that it is NOT an error if the + // merchant does not grant a refund. + auto_refund?: RelativeTime; + + // Extra data that is only interpreted by the merchant frontend. + // Useful when the merchant needs to store extra information on a + // contract without storing it separately in their database. + extra?: any; + } + +} diff --git a/packages/backend/src/hooks/async.ts b/packages/backend/src/hooks/async.ts new file mode 100644 index 0000000..fd55004 --- /dev/null +++ b/packages/backend/src/hooks/async.ts @@ -0,0 +1,76 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ +import { useState } from "preact/hooks"; +import { cancelPendingRequest } from "./backend"; + +export interface Options { + slowTolerance: number, +} + +export interface AsyncOperationApi { + request: (...a: any) => void, + cancel: () => void, + data: T | undefined, + isSlow: boolean, + isLoading: boolean, + error: string | undefined +} + +export function useAsync(fn?: (...args: any) => Promise, { slowTolerance: tooLong }: Options = { slowTolerance: 1000 }): AsyncOperationApi { + const [data, setData] = useState(undefined); + const [isLoading, setLoading] = useState(false); + const [error, setError] = useState(undefined); + const [isSlow, setSlow] = useState(false) + + const request = async (...args: any) => { + if (!fn) return; + setLoading(true); + + const handler = setTimeout(() => { + setSlow(true) + }, tooLong) + + try { + const result = await fn(...args); + setData(result); + } catch (error) { + setError(error); + } + setLoading(false); + setSlow(false) + clearTimeout(handler) + }; + + function cancel() { + cancelPendingRequest() + setLoading(false); + setSlow(false) + } + + return { + request, + cancel, + data, + isSlow, + isLoading, + error + }; +} diff --git a/packages/backend/src/hooks/backend.ts b/packages/backend/src/hooks/backend.ts new file mode 100644 index 0000000..96b8f71 --- /dev/null +++ b/packages/backend/src/hooks/backend.ts @@ -0,0 +1,262 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { mutate, cache } from 'swr'; +import axios, { AxiosError, AxiosResponse } from 'axios' +import { MerchantBackend } from '../declaration'; +import { useBackendContext } from '../context/backend'; +import { useEffect, useState } from 'preact/hooks'; +import { DEFAULT_REQUEST_TIMEOUT } from '../utils/constants'; + +export function mutateAll(re: RegExp, value?: unknown): Array> { + return cache.keys().filter(key => { + return re.test(key) + }).map(key => { + return mutate(key, value) + }) +} + +export type HttpResponse = HttpResponseOk | HttpResponseLoading | HttpError; +export type HttpResponsePaginated = HttpResponseOkPaginated | HttpResponseLoading | HttpError; + +export interface RequestInfo { + url: string; + hasToken: boolean; + params: unknown; + data: unknown; +} + +interface HttpResponseLoading { + ok?: false; + loading: true; + clientError?: false; + serverError?: false; + + data?: T; +} +export interface HttpResponseOk { + ok: true; + loading?: false; + clientError?: false; + serverError?: false; + + data: T; + info?: RequestInfo; +} + +export type HttpResponseOkPaginated = HttpResponseOk & WithPagination + +export interface WithPagination { + loadMore: () => void; + loadMorePrev: () => void; + isReachingEnd?: boolean; + isReachingStart?: boolean; +} + +export type HttpError = HttpResponseClientError | HttpResponseServerError | HttpResponseUnexpectedError; +export interface SwrError { + info: unknown, + status: number, + message: string, +} +export interface HttpResponseServerError { + ok?: false; + loading?: false; + clientError?: false; + serverError: true; + + error?: MerchantBackend.ErrorDetail; + status: number; + message: string; + info?: RequestInfo; +} +interface HttpResponseClientError { + ok?: false; + loading?: false; + clientError: true; + serverError?: false; + + info?: RequestInfo; + isUnauthorized: boolean; + isNotfound: boolean; + status: number; + error?: MerchantBackend.ErrorDetail; + message: string; + +} + +interface HttpResponseUnexpectedError { + ok?: false; + loading?: false; + clientError?: false; + serverError?: false; + + info?: RequestInfo; + status?: number; + error: unknown; + message: string; +} + +type Methods = 'get' | 'post' | 'patch' | 'delete' | 'put'; + +interface RequestOptions { + method?: Methods; + token?: string; + data?: unknown; + params?: unknown; +} + +function buildRequestOk(res: AxiosResponse, url: string, hasToken: boolean): HttpResponseOk { + return { + ok: true, data: res.data, info: { + params: res.config.params, + data: res.config.data, + url, + hasToken, + } + } +} + +// function buildResponse(data?: T, error?: MerchantBackend.ErrorDetail, isValidating?: boolean): HttpResponse { +// if (isValidating) return {loading: true} +// if (error) return buildRequestFailed() +// } + +function buildRequestFailed(ex: AxiosError, url: string, hasToken: boolean): HttpResponseClientError | HttpResponseServerError | HttpResponseUnexpectedError { + const status = ex.response?.status + + const info: RequestInfo = { + data: ex.request?.data, + params: ex.request?.params, + url, + hasToken, + }; + + if (status && status >= 400 && status < 500) { + const error: HttpResponseClientError = { + clientError: true, + isNotfound: status === 404, + isUnauthorized: status === 401, + status, + info, + message: ex.response?.data?.hint || ex.message, + error: ex.response?.data + } + return error + } + if (status && status >= 500 && status < 600) { + const error: HttpResponseServerError = { + serverError: true, + status, + info, + message: `${ex.response?.data?.hint} (code ${ex.response?.data?.code})` || ex.message, + error: ex.response?.data + } + return error; + } + + const error: HttpResponseUnexpectedError = { + info, + status, + error: ex, + message: ex.message + } + + return error +} + + +const CancelToken = axios.CancelToken; +let source = CancelToken.source(); + +export function cancelPendingRequest() { + source.cancel('canceled by the user') + source = CancelToken.source() +} + +let removeAxiosCancelToken = false +/** + * Jest mocking seems to break when using the cancelToken property. + * Using this workaround when testing while finding the correct solution + */ +export function setAxiosRequestAsTestingEnvironment() { + removeAxiosCancelToken = true +} + +export async function request(url: string, options: RequestOptions = {}): Promise> { + const headers = options.token ? { Authorization: `Bearer ${options.token}` } : undefined + + try { + const res = await axios({ + url, + responseType: 'json', + headers, + cancelToken: !removeAxiosCancelToken? source.token : undefined, + method: options.method || 'get', + data: options.data, + params: options.params, + timeout: DEFAULT_REQUEST_TIMEOUT * 1000, + }) + return buildRequestOk(res, url, !!options.token) + } catch (e) { + const error = buildRequestFailed(e, url, !!options.token) + throw error + } + +} + +export function fetcher(url: string, token: string, backend: string): Promise> { + return request(`${backend}${url}`, { token }) +} + +export function useBackendInstancesTestForAdmin(): HttpResponse { + const { url, token } = useBackendContext() + + type Type = MerchantBackend.Instances.InstancesResponse; + + const [result, setResult] = useState>({ loading: true }) + + useEffect(() => { + request(`${url}/management/instances`, { token }) + .then(data => setResult(data)) + .catch(error => setResult(error)) + }, [url, token]) + + + return result +} + + +export function useBackendConfig(): HttpResponse { + const { url, token } = useBackendContext() + + type Type = MerchantBackend.VersionResponse; + + const [result, setResult] = useState>({ loading: true }) + + useEffect(() => { + request(`${url}/config`, { token }) + .then(data => setResult(data)) + .catch(error => setResult(error)) + }, [url, token]) + + return result +} diff --git a/packages/backend/src/hooks/index.ts b/packages/backend/src/hooks/index.ts new file mode 100644 index 0000000..19d672a --- /dev/null +++ b/packages/backend/src/hooks/index.ts @@ -0,0 +1,110 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { StateUpdater, useCallback, useState } from "preact/hooks"; +import { ValueOrFunction } from '../utils/types'; + + +const calculateRootPath = () => { + const rootPath = typeof window !== undefined ? window.location.origin + window.location.pathname : '/' + return rootPath +} + +export function useBackendURL(url?: string): [string, boolean, StateUpdater, () => void] { + const [value, setter] = useNotNullLocalStorage('backend-url', url || calculateRootPath()) + const [triedToLog, setTriedToLog] = useLocalStorage('tried-login') + + const checkedSetter = (v: ValueOrFunction) => { + setTriedToLog('yes') + return setter(p => (v instanceof Function ? v(p) : v).replace(/\/$/, '')) + } + + const resetBackend = () => { + setTriedToLog(undefined) + } + return [value, !!triedToLog, checkedSetter, resetBackend] +} + +export function useBackendDefaultToken(): [string | undefined, StateUpdater] { + return useLocalStorage('backend-token') +} + +export function useBackendInstanceToken(id: string): [string | undefined, StateUpdater] { + const [token, setToken] = useLocalStorage(`backend-token-${id}`) + const [defaultToken, defaultSetToken] = useBackendDefaultToken() + + // instance named 'default' use the default token + if (id === 'default') { + return [defaultToken, defaultSetToken] + } + + return [token, setToken] +} + +export function useLang(initial?: string): [string, StateUpdater] { + const browserLang = typeof window !== "undefined" ? navigator.language || (navigator as any).userLanguage : undefined; + const defaultLang = (browserLang || initial || 'en').substring(0, 2) + return useNotNullLocalStorage('lang-preference', defaultLang) +} + +export function useLocalStorage(key: string, initialValue?: string): [string | undefined, StateUpdater] { + const [storedValue, setStoredValue] = useState((): string | undefined => { + return typeof window !== "undefined" ? window.localStorage.getItem(key) || initialValue : initialValue; + }); + + const setValue = (value?: string | ((val?: string) => string | undefined)) => { + setStoredValue(p => { + const toStore = value instanceof Function ? value(p) : value + if (typeof window !== "undefined") { + if (!toStore) { + window.localStorage.removeItem(key) + } else { + window.localStorage.setItem(key, toStore); + } + } + return toStore + }) + }; + + return [storedValue, setValue]; +} + +export function useNotNullLocalStorage(key: string, initialValue: string): [string, StateUpdater] { + const [storedValue, setStoredValue] = useState((): string => { + return typeof window !== "undefined" ? window.localStorage.getItem(key) || initialValue : initialValue; + }); + + const setValue = (value: string | ((val: string) => string)) => { + const valueToStore = value instanceof Function ? value(storedValue) : value; + setStoredValue(valueToStore); + if (typeof window !== "undefined") { + if (!valueToStore) { + window.localStorage.removeItem(key) + } else { + window.localStorage.setItem(key, valueToStore); + } + } + }; + + return [storedValue, setValue]; +} + + diff --git a/packages/backend/src/hooks/instance.ts b/packages/backend/src/hooks/instance.ts new file mode 100644 index 0000000..14ab8de --- /dev/null +++ b/packages/backend/src/hooks/instance.ts @@ -0,0 +1,187 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ +import { MerchantBackend } from '../declaration'; +import { useBackendContext } from '../context/backend'; +import { fetcher, HttpError, HttpResponse, HttpResponseOk, request, SwrError } from './backend'; +import useSWR, { mutate } from 'swr'; +import { useInstanceContext } from '../context/instance'; + + +interface InstanceAPI { + updateInstance: (data: MerchantBackend.Instances.InstanceReconfigurationMessage) => Promise; + deleteInstance: () => Promise; + clearToken: () => Promise; + setNewToken: (token: string) => Promise; +} + +export function useManagementAPI(instanceId: string) : InstanceAPI { + const { url, token } = useBackendContext() + + const updateInstance = async (instance: MerchantBackend.Instances.InstanceReconfigurationMessage): Promise => { + await request(`${url}/management/instances/${instanceId}`, { + method: 'patch', + token, + data: instance + }) + + mutate([`/private/`, token, url], null) + }; + + const deleteInstance = async (): Promise => { + await request(`${url}/management/instances/${instanceId}`, { + method: 'delete', + token, + }) + + mutate([`/private/`, token, url], null) + } + + const clearToken = async (): Promise => { + await request(`${url}/management/instances/${instanceId}/auth`, { + method: 'post', + token, + data: { method: 'external' } + }) + + mutate([`/private/`, token, url], null) + } + + const setNewToken = async (newToken: string): Promise => { + await request(`${url}/management/instances/${instanceId}/auth`, { + method: 'post', + token, + data: { method: 'token', token: newToken } + }) + + mutate([`/private/`, token, url], null) + } + + return { updateInstance, deleteInstance, setNewToken, clearToken } +} + +export function useInstanceAPI(): InstanceAPI { + const { url: baseUrl, token: adminToken } = useBackendContext() + const { token: instanceToken, id, admin } = useInstanceContext() + + const { url, token } = !admin ? { + url: baseUrl, token: adminToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + const updateInstance = async (instance: MerchantBackend.Instances.InstanceReconfigurationMessage): Promise => { + await request(`${url}/private/`, { + method: 'patch', + token, + data: instance + }) + + if (adminToken) mutate(['/private/instances', adminToken, baseUrl], null) + mutate([`/private/`, token, url], null) + }; + + const deleteInstance = async (): Promise => { + await request(`${url}/private/`, { + method: 'delete', + token: adminToken, + }) + + if (adminToken) mutate(['/private/instances', adminToken, baseUrl], null) + mutate([`/private/`, token, url], null) + } + + const clearToken = async (): Promise => { + await request(`${url}/private/auth`, { + method: 'post', + token, + data: { method: 'external' } + }) + + mutate([`/private/`, token, url], null) + } + + const setNewToken = async (newToken: string): Promise => { + await request(`${url}/private/auth`, { + method: 'post', + token, + data: { method: 'token', token: newToken } + }) + + mutate([`/private/`, token, url], null) + } + + return { updateInstance, deleteInstance, setNewToken, clearToken } +} + + +export function useInstanceDetails(): HttpResponse { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + } + + const { data, error, isValidating } = useSWR, HttpError>([`/private/`, token, url], fetcher, { + refreshInterval:0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + errorRetryCount: 0, + errorRetryInterval: 1, + shouldRetryOnError: false, + }) + + if (isValidating) return {loading:true, data: data?.data} + if (data) return data + if (error) return error + return {loading: true} +} + +export function useManagedInstanceDetails(instanceId: string): HttpResponse { + const { url, token } = useBackendContext(); + + const { data, error, isValidating } = useSWR, HttpError>([`/management/instances/${instanceId}`, token, url], fetcher, { + refreshInterval:0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + errorRetryCount: 0, + errorRetryInterval: 1, + shouldRetryOnError: false, + }) + + if (isValidating) return {loading:true, data: data?.data} + if (data) return data + if (error) return error + return {loading: true} +} + +export function useBackendInstances(): HttpResponse { + const { url } = useBackendContext() + const { token } = useInstanceContext(); + + const { data, error, isValidating } = useSWR, HttpError>(['/management/instances', token, url], fetcher) + + if (isValidating) return {loading:true, data: data?.data} + if (data) return data + if (error) return error + return {loading: true} +} diff --git a/packages/backend/src/hooks/listener.ts b/packages/backend/src/hooks/listener.ts new file mode 100644 index 0000000..231ed6c --- /dev/null +++ b/packages/backend/src/hooks/listener.ts @@ -0,0 +1,68 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { useState } from "preact/hooks"; + +/** + * returns subscriber and activator + * subscriber will receive a method (listener) that will be call when the activator runs. + * the result of calling the listener will be sent to @action + * + * @param action from to + * @returns activator and subscriber, undefined activator means that there is not subscriber + */ + +export function useListener(action: (r: T) => Promise): [undefined | (() => Promise), (listener?: () => T) => void] { + type RunnerHandler = { toBeRan?: () => Promise; }; + const [state, setState] = useState({}); + + /** + * subscriber will receive a method that will be call when the activator runs + * + * @param listener function to be run when the activator runs + */ + const subscriber = (listener?: () => T) => { + if (listener) { + setState({ + toBeRan: () => { + const whatWeGetFromTheListener = listener(); + return action(whatWeGetFromTheListener); + } + }); + } else { + setState({ + toBeRan: undefined + }) + } + }; + + /** + * activator will call runner if there is someone subscribed + */ + const activator = state.toBeRan ? async () => { + if (state.toBeRan) { + return state.toBeRan(); + } + return Promise.reject(); + } : undefined; + + return [activator, subscriber]; +} diff --git a/packages/backend/src/hooks/notification.ts b/packages/backend/src/hooks/notification.ts new file mode 100644 index 0000000..d1dfbff --- /dev/null +++ b/packages/backend/src/hooks/notification.ts @@ -0,0 +1,43 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { useCallback, useState } from "preact/hooks"; +import { Notification } from '../utils/types'; + +interface Result { + notification?: Notification; + pushNotification: (n: Notification) => void; + removeNotification: () => void; +} + +export function useNotification(): Result { + const [notification, setNotifications] = useState(undefined) + + const pushNotification = useCallback((n: Notification): void => { + setNotifications(n) + },[]) + + const removeNotification = useCallback(() => { + setNotifications(undefined) + },[]) + + return { notification, pushNotification, removeNotification } +} diff --git a/packages/backend/src/hooks/notifications.ts b/packages/backend/src/hooks/notifications.ts new file mode 100644 index 0000000..1c0c373 --- /dev/null +++ b/packages/backend/src/hooks/notifications.ts @@ -0,0 +1,48 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { useState } from "preact/hooks"; +import { Notification } from '../utils/types'; + +interface Result { + notifications: Notification[]; + pushNotification: (n: Notification) => void; + removeNotification: (n: Notification) => void; +} + +type NotificationWithDate = Notification & { since: Date } + +export function useNotifications(initial: Notification[] = [], timeout = 3000): Result { + const [notifications, setNotifications] = useState<(NotificationWithDate)[]>(initial.map(i => ({...i, since: new Date() }))) + + const pushNotification = (n: Notification): void => { + const entry = { ...n, since: new Date() } + setNotifications(ns => [...ns, entry]) + if (n.type !== 'ERROR') setTimeout(() => { + setNotifications(ns => ns.filter(x => x.since !== entry.since)) + }, timeout) + } + + const removeNotification = (notif: Notification) => { + setNotifications((ns: NotificationWithDate[]) => ns.filter(n => n !== notif)) + } + return { notifications, pushNotification, removeNotification } +} diff --git a/packages/backend/src/hooks/order.ts b/packages/backend/src/hooks/order.ts new file mode 100644 index 0000000..a0d7916 --- /dev/null +++ b/packages/backend/src/hooks/order.ts @@ -0,0 +1,217 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ +import { useEffect, useState } from 'preact/hooks'; +import useSWR from 'swr'; +import { useBackendContext } from '../context/backend'; +import { useInstanceContext } from '../context/instance'; +import { MerchantBackend } from '../declaration'; +import { MAX_RESULT_SIZE, PAGE_SIZE } from '../utils/constants'; +import { fetcher, HttpError, HttpResponse, HttpResponseOk, HttpResponsePaginated, mutateAll, request } from './backend'; + +export interface OrderAPI { + //FIXME: add OutOfStockResponse on 410 + createOrder: (data: MerchantBackend.Orders.PostOrderRequest) => Promise>; + forgetOrder: (id: string, data: MerchantBackend.Orders.ForgetRequest) => Promise>; + refundOrder: (id: string, data: MerchantBackend.Orders.RefundRequest) => Promise>; + deleteOrder: (id: string) => Promise>; + getPaymentURL: (id: string) => Promise>; +} + +type YesOrNo = 'yes' | 'no'; + + +export function orderFetcher(url: string, token: string, backend: string, paid?: YesOrNo, refunded?: YesOrNo, wired?: YesOrNo, searchDate?: Date, delta?: number): Promise> { + const date_ms = delta && delta < 0 && searchDate ? searchDate.getTime() + 1 : searchDate?.getTime() + const params: any = {} + if (paid !== undefined) params.paid = paid + if (delta !== undefined) params.delta = delta + if (refunded !== undefined) params.refunded = refunded + if (wired !== undefined) params.wired = wired + if (date_ms !== undefined) params.date_ms = date_ms + return request(`${backend}${url}`, { token, params }) +} + + +export function useOrderAPI(): OrderAPI { + const { url: baseUrl, token: adminToken } = useBackendContext() + const { token: instanceToken, id, admin } = useInstanceContext() + + const { url, token } = !admin ? { + url: baseUrl, token: adminToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + } + + const createOrder = async (data: MerchantBackend.Orders.PostOrderRequest): Promise> => { + const res = await request(`${url}/private/orders`, { + method: 'post', + token, + data + }) + await mutateAll(/@"\/private\/orders"@/) + return res + } + const refundOrder = async (orderId: string, data: MerchantBackend.Orders.RefundRequest): Promise> => { + mutateAll(/@"\/private\/orders"@/) + return request(`${url}/private/orders/${orderId}/refund`, { + method: 'post', + token, + data + }) + + // return res + } + + const forgetOrder = async (orderId: string, data: MerchantBackend.Orders.ForgetRequest): Promise> => { + mutateAll(/@"\/private\/orders"@/) + return request(`${url}/private/orders/${orderId}/forget`, { + method: 'patch', + token, + data + }) + + } + const deleteOrder = async (orderId: string): Promise> => { + mutateAll(/@"\/private\/orders"@/) + return request(`${url}/private/orders/${orderId}`, { + method: 'delete', + token + }) + } + + const getPaymentURL = async (orderId: string): Promise> => { + return request(`${url}/private/orders/${orderId}`, { + method: 'get', + token + }).then((res) => { + const url = res.data.order_status === "unpaid" ? res.data.taler_pay_uri : res.data.contract_terms.fulfillment_url + const response: HttpResponseOk = res as any + response.data = url || '' + return response + }) + } + + return { createOrder, forgetOrder, deleteOrder, refundOrder, getPaymentURL } +} + +export function useOrderDetails(oderId: string): HttpResponse { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + const { data, error, isValidating } = useSWR, HttpError>([`/private/orders/${oderId}`, token, url], fetcher, { + refreshInterval:0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + }) + + if (isValidating) return { loading: true, data: data?.data } + if (data) return data + if (error) return error + return { loading: true } +} + +export interface InstanceOrderFilter { + paid?: YesOrNo; + refunded?: YesOrNo; + wired?: YesOrNo; + date?: Date; +} + +export function useInstanceOrders(args?: InstanceOrderFilter, updateFilter?: (d: Date) => void): HttpResponsePaginated { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + } + + const [pageBefore, setPageBefore] = useState(1) + const [pageAfter, setPageAfter] = useState(1) + + const totalAfter = pageAfter * PAGE_SIZE; + const totalBefore = args?.date ? pageBefore * PAGE_SIZE : 0; + + /** + * FIXME: this can be cleaned up a little + * + * the logic of double query should be inside the orderFetch so from the hook perspective and cache + * is just one query and one error status + */ + const { data: beforeData, error: beforeError, isValidating: loadingBefore } = useSWR, HttpError>( + [`/private/orders`, token, url, args?.paid, args?.refunded, args?.wired, args?.date, totalBefore], + orderFetcher, + ) + const { data: afterData, error: afterError, isValidating: loadingAfter } = useSWR, HttpError>( + [`/private/orders`, token, url, args?.paid, args?.refunded, args?.wired, args?.date, -totalAfter], + orderFetcher, + ) + + //this will save last result + const [lastBefore, setLastBefore] = useState>({ loading: true }) + const [lastAfter, setLastAfter] = useState>({ loading: true }) + useEffect(() => { + if (afterData) setLastAfter(afterData) + if (beforeData) setLastBefore(beforeData) + }, [afterData, beforeData]) + + // this has problems when there are some ids missing + + if (beforeError) return beforeError + if (afterError) return afterError + + + const pagination = { + isReachingEnd: afterData && afterData.data.orders.length < totalAfter, + isReachingStart: (!args?.date) || (beforeData && beforeData.data.orders.length < totalBefore), + loadMore: () => { + if (!afterData) return + if (afterData.data.orders.length < MAX_RESULT_SIZE) { + setPageAfter(pageAfter + 1) + } else { + const from = afterData.data.orders[afterData.data.orders.length - 1].timestamp.t_ms + if (from && updateFilter) updateFilter(new Date(from)) + } + }, + loadMorePrev: () => { + if (!beforeData) return + if (beforeData.data.orders.length < MAX_RESULT_SIZE) { + setPageBefore(pageBefore + 1) + } else if (beforeData) { + const from = beforeData.data.orders[beforeData.data.orders.length - 1].timestamp.t_ms + if (from && updateFilter) updateFilter(new Date(from)) + } + }, + } + + const orders = !beforeData || !afterData ? [] : (beforeData || lastBefore).data.orders.slice().reverse().concat((afterData || lastAfter).data.orders) + if (loadingAfter || loadingBefore) return { loading: true, data: { orders } } + if (beforeData && afterData) { + return { ok: true, data: { orders }, ...pagination } + } + return { loading: true } + +} + diff --git a/packages/backend/src/hooks/product.ts b/packages/backend/src/hooks/product.ts new file mode 100644 index 0000000..edba27b --- /dev/null +++ b/packages/backend/src/hooks/product.ts @@ -0,0 +1,199 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ +import { useEffect } from 'preact/hooks'; +import useSWR, { trigger, useSWRInfinite, cache, mutate } from 'swr'; +import { useBackendContext } from '../context/backend'; +// import { useFetchContext } from '../context/fetch'; +import { useInstanceContext } from '../context/instance'; +import { MerchantBackend, WithId } from '../declaration'; +import { fetcher, HttpError, HttpResponse, HttpResponseOk, mutateAll, request } from './backend'; + +export interface ProductAPI { + createProduct: (data: MerchantBackend.Products.ProductAddDetail) => Promise; + updateProduct: (id: string, data: MerchantBackend.Products.ProductPatchDetail) => Promise; + deleteProduct: (id: string) => Promise; + lockProduct: (id: string, data: MerchantBackend.Products.LockRequest) => Promise; +} + + +export function useProductAPI(): ProductAPI { + const { url: baseUrl, token: adminToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: adminToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + + const createProduct = async (data: MerchantBackend.Products.ProductAddDetail): Promise => { + await request(`${url}/private/products`, { + method: 'post', + token, + data + }); + + await mutateAll(/@"\/private\/products"@/, null); + }; + + const updateProduct = async (productId: string, data: MerchantBackend.Products.ProductPatchDetail): Promise => { + const r = await request(`${url}/private/products/${productId}`, { + method: 'patch', + token, + data + }); + + /** + * There is some inconsistency in how the cache is evicted. + * I'm keeping this for later inspection + */ + + // -- Clear all cache + // -- This seems to work always but is bad + + // const keys = [...cache.keys()] + // console.log(keys) + // cache.clear() + // await Promise.all(keys.map(k => trigger(k))) + + // -- From the keys to the cache trigger + // -- An intermediate step + + // const keys = [ + // [`/private/products`, token, url], + // [`/private/products/${productId}`, token, url], + // ] + // cache.clear() + // const f: string[][] = keys.map(k => cache.serializeKey(k)) + // console.log(f) + // const m = flat(f) + // console.log(m) + // await Promise.all(m.map(k => trigger(k, true))) + + // await Promise.all(keys.map(k => mutate(k))) + + // -- This is how is supposed to be use + + // await mutate([`/private/products`, token, url]) + // await mutate([`/private/products/${productId}`, token, url]) + + // await mutateAll(/@"\/private\/products"@/); + await mutateAll(/@"\/private\/products\/.*"@/); + // return true + // return r + + // -- FIXME: why this un-break the tests? + return Promise.resolve() + }; + + const deleteProduct = async (productId: string): Promise => { + await request(`${url}/private/products/${productId}`, { + method: 'delete', + token, + }); + + await mutateAll(/@"\/private\/products"@/); + }; + + const lockProduct = async (productId: string, data: MerchantBackend.Products.LockRequest): Promise => { + await request(`${url}/private/products/${productId}/lock`, { + method: 'post', + token, + data + }); + + await mutateAll(/@"\/private\/products"@/); + }; + + return { createProduct, updateProduct, deleteProduct, lockProduct }; +} + + +export function useInstanceProducts(): HttpResponse<(MerchantBackend.Products.ProductDetail & WithId)[]> { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + // const { useSWR, useSWRInfinite } = useFetchContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + const { data: list, error: listError, isValidating: listLoading } = useSWR, HttpError>([`/private/products`, token, url], fetcher, { + refreshInterval: 0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + }); + + const { data: products, error: productError, setSize, size } = useSWRInfinite, HttpError>((pageIndex: number) => { + if (!list?.data || !list.data.products.length || listError || listLoading) return null + return [`/private/products/${list.data.products[pageIndex].product_id}`, token, url] + }, fetcher, { + revalidateAll: true, + }) + + useEffect(() => { + if (list?.data && list.data.products.length > 0) { + setSize(list.data.products.length) + } + }, [list?.data.products.length, listLoading]) + + + if (listLoading) return { loading: true, data: [] } + if (listError) return listError + if (productError) return productError + if (list?.data && list.data.products.length === 0) { + return { ok: true, data: [] } + } + if (products) { + const dataWithId = products.map((d) => { + //take the id from the queried url + return ({ ...d.data, id: d.info?.url.replace(/.*\/private\/products\//, '') || '' }) + }) + return { ok: true, data: dataWithId } + } + return { loading: true } +} + +export function useProductDetails(productId: string): HttpResponse { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + const { data, error, isValidating } = useSWR, HttpError>( + [`/private/products/${productId}`, token, url], fetcher, { + refreshInterval: 0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + } + ) + + if (isValidating) return { loading: true, data: data?.data } + if (data) return data + if (error) return error + return { loading: true } +} diff --git a/packages/backend/src/hooks/tips.ts b/packages/backend/src/hooks/tips.ts new file mode 100644 index 0000000..345e1fa --- /dev/null +++ b/packages/backend/src/hooks/tips.ts @@ -0,0 +1,159 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ +import useSWR from 'swr'; +import { useBackendContext } from '../context/backend'; +import { useInstanceContext } from '../context/instance'; +import { MerchantBackend } from '../declaration'; +import { fetcher, HttpError, HttpResponse, HttpResponseOk, mutateAll, request } from './backend'; + + +export function useReservesAPI(): ReserveMutateAPI { + const { url: baseUrl, token: adminToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: adminToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + const createReserve = async (data: MerchantBackend.Tips.ReserveCreateRequest): Promise> => { + const res = await request(`${url}/private/reserves`, { + method: 'post', + token, + data + }); + + await mutateAll(/@"\/private\/reserves"@/); + + return res + }; + + const authorizeTipReserve = async (pub: string, data: MerchantBackend.Tips.TipCreateRequest): Promise> => { + const res = await request(`${url}/private/reserves/${pub}/authorize-tip`, { + method: 'post', + token, + data + }); + await mutateAll(/@"\/private\/reserves"@/); + + return res + }; + + const authorizeTip = async (data: MerchantBackend.Tips.TipCreateRequest): Promise> => { + const res = await request(`${url}/private/tips`, { + method: 'post', + token, + data + }); + + await mutateAll(/@"\/private\/reserves"@/); + + return res + }; + + const deleteReserve = async (pub: string): Promise> => { + const res = await request(`${url}/private/reserves/${pub}`, { + method: 'delete', + token, + }); + + await mutateAll(/@"\/private\/reserves"@/); + + return res + }; + + + return { createReserve, authorizeTip, authorizeTipReserve, deleteReserve }; +} + +export interface ReserveMutateAPI { + createReserve: (data: MerchantBackend.Tips.ReserveCreateRequest) => Promise>; + authorizeTipReserve: (id: string, data: MerchantBackend.Tips.TipCreateRequest) => Promise>; + authorizeTip: (data: MerchantBackend.Tips.TipCreateRequest) => Promise>; + deleteReserve: (id: string) => Promise>; +} + +export function useInstanceTips(): HttpResponse { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + } + + const { data, error, isValidating } = useSWR, HttpError>([`/private/reserves`, token, url], fetcher) + + if (isValidating) return { loading: true, data: data?.data } + if (data) return data + if (error) return error + return { loading: true } +} + + +export function useReserveDetails(reserveId: string): HttpResponse { + const { url: baseUrl } = useBackendContext(); + const { token, id: instanceId, admin } = useInstanceContext(); + + const url = !admin ? baseUrl : `${baseUrl}/instances/${instanceId}` + + const { data, error, isValidating } = useSWR, HttpError>([`/private/reserves/${reserveId}`, token, url], reserveDetailFetcher, { + refreshInterval:0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + }) + + if (isValidating) return { loading: true, data: data?.data } + if (data) return data + if (error) return error + return { loading: true } +} + +export function useTipDetails(tipId: string): HttpResponse { + const { url: baseUrl } = useBackendContext(); + const { token, id: instanceId, admin } = useInstanceContext(); + + const url = !admin ? baseUrl : `${baseUrl}/instances/${instanceId}` + + const { data, error, isValidating } = useSWR, HttpError>([`/private/tips/${tipId}`, token, url], tipsDetailFetcher, { + refreshInterval:0, + refreshWhenHidden: false, + revalidateOnFocus: false, + revalidateOnReconnect: false, + refreshWhenOffline: false, + }) + + if (isValidating) return { loading: true, data: data?.data } + if (data) return data + if (error) return error + return { loading: true } +} + +export function reserveDetailFetcher(url: string, token: string, backend: string): Promise> { + return request(`${backend}${url}`, { token, params: { + tips: 'yes' + } }) +} + +export function tipsDetailFetcher(url: string, token: string, backend: string): Promise> { + return request(`${backend}${url}`, { token, params: { + pickups: 'yes' + } }) +} diff --git a/packages/backend/src/hooks/transfer.ts b/packages/backend/src/hooks/transfer.ts new file mode 100644 index 0000000..02e041a --- /dev/null +++ b/packages/backend/src/hooks/transfer.ts @@ -0,0 +1,150 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ +import { MerchantBackend } from '../declaration'; +import { useBackendContext } from '../context/backend'; +import { request, mutateAll, HttpResponse, HttpError, HttpResponseOk, HttpResponsePaginated } from './backend'; +import useSWR from 'swr'; +import { useInstanceContext } from '../context/instance'; +import { MAX_RESULT_SIZE, PAGE_SIZE } from '../utils/constants'; +import { useEffect, useState } from 'preact/hooks'; + +async function transferFetcher(url: string, token: string, backend: string, payto_uri?: string, verified?: string, position?: string, delta?: number): Promise> { + const params: any = {} + if (payto_uri !== undefined) params.payto_uri = payto_uri + if (verified !== undefined) params.verified = verified + if (delta !== undefined) { + // if (delta > 0) { + // params.after = searchDate?.getTime() + // } else { + // params.before = searchDate?.getTime() + // } + params.limit = delta + } + if (position !== undefined) params.offset = position + + return request(`${backend}${url}`, { token, params }) +} + +export function useTransferAPI(): TransferAPI { + const { url: baseUrl, token: adminToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: adminToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + }; + + const informTransfer = async (data: MerchantBackend.Transfers.TransferInformation): Promise> => { + mutateAll(/@"\/private\/transfers"@/); + + return request(`${url}/private/transfers`, { + method: 'post', + token, + data + }); + }; + + return { informTransfer }; +} + +export interface TransferAPI { + informTransfer: (data: MerchantBackend.Transfers.TransferInformation) => Promise>; +} + +export interface InstanceTransferFilter { + payto_uri?: string; + verified?: 'yes' | 'no'; + position?: string; +} + + +export function useInstanceTransfers(args?: InstanceTransferFilter, updatePosition?: (id: string) => void): HttpResponsePaginated { + const { url: baseUrl, token: baseToken } = useBackendContext(); + const { token: instanceToken, id, admin } = useInstanceContext(); + + const { url, token } = !admin ? { + url: baseUrl, token: baseToken + } : { + url: `${baseUrl}/instances/${id}`, token: instanceToken + } + + const [pageBefore, setPageBefore] = useState(1) + const [pageAfter, setPageAfter] = useState(1) + + const totalAfter = pageAfter * PAGE_SIZE; + const totalBefore = args?.position !== undefined ? pageBefore * PAGE_SIZE : 0; + + /** + * FIXME: this can be cleaned up a little + * + * the logic of double query should be inside the orderFetch so from the hook perspective and cache + * is just one query and one error status + */ + const { data: beforeData, error: beforeError, isValidating: loadingBefore } = useSWR, HttpError>( + [`/private/transfers`, token, url, args?.payto_uri, args?.verified, args?.position, totalBefore], + transferFetcher, + ) + const { data: afterData, error: afterError, isValidating: loadingAfter } = useSWR, HttpError>( + [`/private/transfers`, token, url, args?.payto_uri, args?.verified, args?.position, -totalAfter], + transferFetcher, + ) + + //this will save last result + const [lastBefore, setLastBefore] = useState>({ loading: true }) + const [lastAfter, setLastAfter] = useState>({ loading: true }) + useEffect(() => { + if (afterData) setLastAfter(afterData) + if (beforeData) setLastBefore(beforeData) + }, [afterData, beforeData]) + + // this has problems when there are some ids missing + + if (beforeError) return beforeError + if (afterError) return afterError + + const pagination = { + isReachingEnd: afterData && afterData.data.transfers.length < totalAfter, + isReachingStart: (!args?.position) || (beforeData && beforeData.data.transfers.length < totalBefore), + loadMore: () => { + if (!afterData) return + if (afterData.data.transfers.length < MAX_RESULT_SIZE) { + setPageAfter(pageAfter + 1) + } else { + const from = ""+afterData.data.transfers[afterData.data.transfers.length - 1].transfer_serial_id + if (from && updatePosition) updatePosition(from) + } + }, + loadMorePrev: () => { + if (!beforeData) return + if (beforeData.data.transfers.length < MAX_RESULT_SIZE) { + setPageBefore(pageBefore + 1) + } else if (beforeData) { + const from = ""+beforeData.data.transfers[beforeData.data.transfers.length - 1].transfer_serial_id + if (from && updatePosition) updatePosition(from) + } + }, + } + + const transfers = !beforeData || !afterData ? [] : (beforeData || lastBefore).data.transfers.slice().reverse().concat((afterData || lastAfter).data.transfers) + if (loadingAfter || loadingBefore) return { loading: true, data: { transfers } } + if (beforeData && afterData) { + return { ok: true, data: { transfers }, ...pagination } + } + return { loading: true } +} + + diff --git a/packages/backend/src/i18n/de.po b/packages/backend/src/i18n/de.po new file mode 100644 index 0000000..6b35bd0 --- /dev/null +++ b/packages/backend/src/i18n/de.po @@ -0,0 +1,1057 @@ +# This file is part of TALER +# (C) 2016 GNUnet e.V. +# +# TALER is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# +# TALER is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# TALER; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "" + +#: src/InstanceRoutes.tsx:110 +#, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:289 +#, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "" + +#: src/components/form/InputDate.tsx:81 +#, c-format +msgid "clear" +msgstr "" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "" + +#: src/components/form/InputLocation.tsx:38 +#, c-format +msgid "Town location" +msgstr "" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:59 +#, c-format +msgid "Product id" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "" + +#: src/components/form/InputStock.tsx:105 +#, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, c-format +msgid "Orders" +msgstr "" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "" + +#: src/components/menu/SideBar.tsx:87 +#, c-format +msgid "Connection" +msgstr "" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "" + +#: src/components/menu/SideBar.tsx:116 +#, c-format +msgid "New" +msgstr "" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, c-format +msgid "Delete" +msgstr "" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, c-format +msgid "Net" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, c-format +msgid "Location" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, c-format +msgid "should be greater than 0" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, c-format +msgid "Order status" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, c-format +msgid "Product list" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, c-format +msgid "could not create the refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:108 +#, c-format +msgid "Refunded" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:109 +#, c-format +msgid "Not wired" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, c-format +msgid "Transfer ID" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, c-format +msgid "Account Address" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, c-format +msgid "could not inform transfer" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, c-format +msgid "load newer transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, c-format +msgid "Confirmed" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, c-format +msgid "Executed at" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, c-format +msgid "load older transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "" diff --git a/packages/backend/src/i18n/en.po b/packages/backend/src/i18n/en.po new file mode 100644 index 0000000..6b35bd0 --- /dev/null +++ b/packages/backend/src/i18n/en.po @@ -0,0 +1,1057 @@ +# This file is part of TALER +# (C) 2016 GNUnet e.V. +# +# TALER is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# +# TALER is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# TALER; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "" + +#: src/InstanceRoutes.tsx:110 +#, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:289 +#, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "" + +#: src/components/form/InputDate.tsx:81 +#, c-format +msgid "clear" +msgstr "" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "" + +#: src/components/form/InputLocation.tsx:38 +#, c-format +msgid "Town location" +msgstr "" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:59 +#, c-format +msgid "Product id" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "" + +#: src/components/form/InputStock.tsx:105 +#, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, c-format +msgid "Orders" +msgstr "" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "" + +#: src/components/menu/SideBar.tsx:87 +#, c-format +msgid "Connection" +msgstr "" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "" + +#: src/components/menu/SideBar.tsx:116 +#, c-format +msgid "New" +msgstr "" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, c-format +msgid "Delete" +msgstr "" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, c-format +msgid "Net" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, c-format +msgid "Location" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, c-format +msgid "should be greater than 0" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, c-format +msgid "Order status" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, c-format +msgid "Product list" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, c-format +msgid "could not create the refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:108 +#, c-format +msgid "Refunded" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:109 +#, c-format +msgid "Not wired" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, c-format +msgid "Transfer ID" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, c-format +msgid "Account Address" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, c-format +msgid "could not inform transfer" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, c-format +msgid "load newer transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, c-format +msgid "Confirmed" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, c-format +msgid "Executed at" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, c-format +msgid "load older transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "" diff --git a/packages/backend/src/i18n/es.po b/packages/backend/src/i18n/es.po new file mode 100644 index 0000000..9075d46 --- /dev/null +++ b/packages/backend/src/i18n/es.po @@ -0,0 +1,1065 @@ +# This file is part of TALER +# (C) 2016 GNUnet e.V. +# +# TALER is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# +# TALER is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# TALER; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "Acceso denegado" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "Verifica que el token sea valido" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "No se pudo acceder al servidor" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "No se pudo inferir el id de la instancia con la url %1$s" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "HTTP status #%1$s: Servidor reporto un problema" + +#: src/InstanceRoutes.tsx:110 +#, fuzzy, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "Recivimos el mensaje %1$s desde %2$s" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "Sin instancia default" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "para usar el merchant backoffice, deberΓ­a crear la instancia default" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "Servidir reporto un problema: HTTP status #%1$s" + +#: src/InstanceRoutes.tsx:289 +#, fuzzy, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "Recivimos el mensaje %1$s desde %2$s" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "Login necesario" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" +"Por favor ingrese su token de autorizaciΓ³n. El token debe tener \"secret-" +"token\" y comenzar con Bearer o ApiKey" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "Confirmar" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "El valor %1$s es invalido para una URL de pago" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "elegir una fecha" + +#: src/components/form/InputDate.tsx:81 +#, fuzzy, c-format +msgid "clear" +msgstr "Limpiar" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "nunca" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "La imagen debe ser mas chica que 1 MB" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "PaΓ­s" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "DirecciΓ³n" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "NΓΊmero de edificio" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "Nombre de edificio" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "Calle" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "CΓ³digo postal" + +#: src/components/form/InputLocation.tsx:38 +#, fuzzy, c-format +msgid "Town location" +msgstr "UbicaciΓ³n de ciudad" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "Ciudad" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "Distrito" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "Provincia" + +#: src/components/form/InputSearchProduct.tsx:59 +#, fuzzy, c-format +msgid "Product id" +msgstr "Id de producto" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "Descripcion" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "Nombre" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "Cargando..." + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "No se encontraron productos" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "Sin resultados" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "Borrando" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "Cambiando" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "Administrar token" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "Actualizar" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "Eliminar" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "Cancelar" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "Administrar stock" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "Inifinito" + +#: src/components/form/InputStock.tsx:105 +#, fuzzy, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "no puede ser mayor al stock actual %1$s" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "stock actual cambiarΓ‘ desde %1$s a %2$s" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "stock actual seguirΓ‘ en %1$s" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "Ingresando" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "Perdido" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "Actual" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "sin stock" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "PrΓ³ximo reabastecimiento" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "DirecciΓ³n de entrega" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "este producto no tiene impuestos" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "Monto" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "Moneda y valor separado por dos puntos" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "Agregar" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "Instancia" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "ConfiguraciΓ³n" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, fuzzy, c-format +msgid "Orders" +msgstr "Ordenes" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "Productos" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "Transferencias" + +#: src/components/menu/SideBar.tsx:87 +#, fuzzy, c-format +msgid "Connection" +msgstr "ConexiΓ³n" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "Instancias" + +#: src/components/menu/SideBar.tsx:116 +#, fuzzy, c-format +msgid "New" +msgstr "Nuevo" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "Lista" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "Salir" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "Limpiar" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "deberΓ­an ser iguales" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "no puede ser igual al anterior" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" +"EstΓ‘ actualizando el token de autorizaciΓ³n para la instancia %1$s con id %2$s" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "Viejo token" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "Nuevo token" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" +"Limpiar el token de autorizaciΓ³n significa acceso publico a la instancia" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "ID" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "Imagen" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "Unidad" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "Precio" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "Stock" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "Impuesto" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "Servidor no encontrado" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "No se pudo aceder al servidor" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "Recivimos el mensaje %1$s desde %2$s" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "Error inesperado" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "Token de autorizaciΓ³n" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "DirecciΓ³n de cuenta" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "Impuesto mΓ‘ximo de deposito por omisiΓ³n" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "Impuesto mΓ‘ximo de transferencia por omisiΓ³n" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "AmortizaciΓ³n de impuesto de transferencia por omisiΓ³n" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "JurisdicciΓ³n" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "Retrazo de pago por omisiΓ³n" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "Retrazo de transferencia por omisiΓ³n" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "no se pudo crear la instancia" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, fuzzy, c-format +msgid "Delete" +msgstr "Borrando" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "No hay instancias todavΓ­an, agregue mas presionando el signo +" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "Productos de inventario" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "Precio total" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "Impuesto total" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "Precio de la orden" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, fuzzy, c-format +msgid "Net" +msgstr "Neto" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "Resumen" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "Opciones de pago" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "Plazo de reembolso automΓ‘tico" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "Plazo de reembolso" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "Plazo de pago" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "Fecha de entrega" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, fuzzy, c-format +msgid "Location" +msgstr "UbicaciΓ³n" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "Impuesto mΓ‘ximo" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "Impuesto de transferencia mΓ‘ximo" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "AmortizaciΓ³n de impuesto de transferencia" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "URL de completitud" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "InformaciΓ³n extra" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "seleccione un producto primero" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, fuzzy, c-format +msgid "should be greater than 0" +msgstr "La imagen debe ser mas chica que 1 MB" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" +"no puede ser mayor al stock actual y la cantidad previamente agregada. " +"mΓ‘ximo: %1$s" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "no puede ser mayor al stock actual %1$s" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "Cantidad" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "Orden" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "reclamado" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "copiar url" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "pagar en" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "creado" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "CronologΓ­a" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "Detalles de pago" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, fuzzy, c-format +msgid "Order status" +msgstr "Estado de orden" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, fuzzy, c-format +msgid "Product list" +msgstr "Lista de producto" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "pagados" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "transferido" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "reembolzado" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "reembolzar" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "Monto reembolzado" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "Total depositado" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "impago" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "URL de estado de orden" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "URI de pago" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" +"Estado de orden desconocido. Esto es un error, por favor contacte a su " +"administrador" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "reembolzo creado satisfactoriamente" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, fuzzy, c-format +msgid "could not create the refund" +msgstr "No se pudo aceder al servidor" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "cargar nuevas ordenes" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "Fecha" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "Reembolzar" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "cargar viejas ordenes" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "No se enconraron ordenes" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "fecha" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "monto" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "razΓ³n" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "MΓ‘ximo reembolzable:" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "RazΓ³n" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "duplicado" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "pedido por el consumidor" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "otro" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "ir a id de orden" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "Pagado" + +#: src/paths/instance/orders/list/index.tsx:108 +#, fuzzy, c-format +msgid "Refunded" +msgstr "Reembolzado" + +#: src/paths/instance/orders/list/index.tsx:109 +#, fuzzy, c-format +msgid "Not wired" +msgstr "No transferido" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "Todo" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "no se pudo crear el producto" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "Venta" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "Ganancia" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "Vendido" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "producto actualizado correctamente" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "no se pudo actualizar el producto" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "producto fue eliminado correctamente" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "no se pudo eliminar el producto" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "Propinas" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "No hay propinas todavΓ­a, agregar mas presionando el signo +" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "no puede ser vacΓ­o" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "verificar el id, no parece vΓ‘lido" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "deberΓ­a tener 52 caracteres, actualmente %1$s" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "La URL no tiene el formato correcto" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, fuzzy, c-format +msgid "Transfer ID" +msgstr "Transferencias" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, fuzzy, c-format +msgid "Account Address" +msgstr "DirecciΓ³n de cuenta" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "URL del Exchange" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, fuzzy, c-format +msgid "could not inform transfer" +msgstr "no se pudo crear la instancia" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, fuzzy, c-format +msgid "load newer transfers" +msgstr "cargar nuevas ordenes" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "CrΓ©dito" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, fuzzy, c-format +msgid "Confirmed" +msgstr "Confirmar" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "Verificado" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, fuzzy, c-format +msgid "Executed at" +msgstr "creado" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "si" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "no" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "desconocido" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, fuzzy, c-format +msgid "load older transfers" +msgstr "cargar viejas transferencias" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "No hay transferencias todavΓ­a, agregar mas presionando el signo +" diff --git a/packages/backend/src/i18n/fr.po b/packages/backend/src/i18n/fr.po new file mode 100644 index 0000000..6b35bd0 --- /dev/null +++ b/packages/backend/src/i18n/fr.po @@ -0,0 +1,1057 @@ +# This file is part of TALER +# (C) 2016 GNUnet e.V. +# +# TALER is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# +# TALER is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# TALER; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "" + +#: src/InstanceRoutes.tsx:110 +#, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:289 +#, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "" + +#: src/components/form/InputDate.tsx:81 +#, c-format +msgid "clear" +msgstr "" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "" + +#: src/components/form/InputLocation.tsx:38 +#, c-format +msgid "Town location" +msgstr "" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:59 +#, c-format +msgid "Product id" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "" + +#: src/components/form/InputStock.tsx:105 +#, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, c-format +msgid "Orders" +msgstr "" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "" + +#: src/components/menu/SideBar.tsx:87 +#, c-format +msgid "Connection" +msgstr "" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "" + +#: src/components/menu/SideBar.tsx:116 +#, c-format +msgid "New" +msgstr "" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, c-format +msgid "Delete" +msgstr "" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, c-format +msgid "Net" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, c-format +msgid "Location" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, c-format +msgid "should be greater than 0" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, c-format +msgid "Order status" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, c-format +msgid "Product list" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, c-format +msgid "could not create the refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:108 +#, c-format +msgid "Refunded" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:109 +#, c-format +msgid "Not wired" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, c-format +msgid "Transfer ID" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, c-format +msgid "Account Address" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, c-format +msgid "could not inform transfer" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, c-format +msgid "load newer transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, c-format +msgid "Confirmed" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, c-format +msgid "Executed at" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, c-format +msgid "load older transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "" diff --git a/packages/backend/src/i18n/index.tsx b/packages/backend/src/i18n/index.tsx new file mode 100644 index 0000000..63c8e19 --- /dev/null +++ b/packages/backend/src/i18n/index.tsx @@ -0,0 +1,203 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** + * Translation helpers for React components and template literals. + */ + +/** + * Imports + */ +import { ComponentChild, ComponentChildren, h, Fragment, VNode } from "preact"; + +import { useTranslationContext } from "../context/translation"; + +export function useTranslator() { + const ctx = useTranslationContext(); + const jed = ctx.handler + return function str(stringSeq: TemplateStringsArray, ...values: any[]): string { + const s = toI18nString(stringSeq); + if (!s) return s + const tr = jed + .translate(s) + .ifPlural(1, s) + .fetch(...values); + return tr; + } +} + + +/** + * Convert template strings to a msgid + */ + function toI18nString(stringSeq: ReadonlyArray): string { + let s = ""; + for (let i = 0; i < stringSeq.length; i++) { + s += stringSeq[i]; + if (i < stringSeq.length - 1) { + s += `%${i + 1}$s`; + } + } + return s; +} + + +interface TranslateSwitchProps { + target: number; + children: ComponentChildren; +} + +function stringifyChildren(children: ComponentChildren): string { + let n = 1; + const ss = (children instanceof Array ? children : [children]).map((c) => { + if (typeof c === "string") { + return c; + } + return `%${n++}$s`; + }); + const s = ss.join("").replace(/ +/g, " ").trim(); + return s; +} + +interface TranslateProps { + children: ComponentChildren; + /** + * Component that the translated element should be wrapped in. + * Defaults to "div". + */ + wrap?: any; + + /** + * Props to give to the wrapped component. + */ + wrapProps?: any; +} + +function getTranslatedChildren( + translation: string, + children: ComponentChildren, +): ComponentChild[] { + const tr = translation.split(/%(\d+)\$s/); + const childArray = children instanceof Array ? children : [children]; + // Merge consecutive string children. + const placeholderChildren = Array(); + for (let i = 0; i < childArray.length; i++) { + const x = childArray[i]; + if (x === undefined) { + continue; + } else if (typeof x === "string") { + continue; + } else { + placeholderChildren.push(x); + } + } + const result = Array(); + for (let i = 0; i < tr.length; i++) { + if (i % 2 == 0) { + // Text + result.push(tr[i]); + } else { + const childIdx = Number.parseInt(tr[i],10) - 1; + result.push(placeholderChildren[childIdx]); + } + } + return result; +} + +/** + * Translate text node children of this component. + * If a child component might produce a text node, it must be wrapped + * in a another non-text element. + * + * Example: + * ``` + * + * Hello. Your score is + * + * ``` + */ +export function Translate({ children }: TranslateProps): VNode { + const s = stringifyChildren(children); + const ctx = useTranslationContext() + const translation: string = ctx.handler.ngettext(s, s, 1); + const result = getTranslatedChildren(translation, children) + return {result}; +} + +/** + * Switch translation based on singular or plural based on the target prop. + * Should only contain TranslateSingular and TransplatePlural as children. + * + * Example: + * ``` + * + * I have {n} apple. + * I have {n} apples. + * + * ``` + */ +export function TranslateSwitch({ children, target }: TranslateSwitchProps) { + let singular: VNode | undefined; + let plural: VNode | undefined; + // const children = this.props.children; + if (children) { + (children instanceof Array ? children : [children]).forEach((child: any) => { + if (child.type === TranslatePlural) { + plural = child; + } + if (child.type === TranslateSingular) { + singular = child; + } + }); + } + if (!singular || !plural) { + console.error("translation not found"); + return h("span", {}, ["translation not found"]); + } + singular.props.target = target; + plural.props.target = target; + // We're looking up the translation based on the + // singular, even if we must use the plural form. + return singular; +} + +interface TranslationPluralProps { + children: ComponentChildren; + target: number; +} + +/** + * See [[TranslateSwitch]]. + */ +export function TranslatePlural({ children, target }: TranslationPluralProps): VNode { + const s = stringifyChildren(children); + const ctx = useTranslationContext() + const translation = ctx.handler.ngettext(s, s, 1); + const result = getTranslatedChildren(translation, children); + return {result}; +} + +/** + * See [[TranslateSwitch]]. + */ +export function TranslateSingular({ children, target }: TranslationPluralProps): VNode { + const s = stringifyChildren(children); + const ctx = useTranslationContext() + const translation = ctx.handler.ngettext(s, s, target); + const result = getTranslatedChildren(translation, children); + return {result}; + +} diff --git a/packages/backend/src/i18n/it.po b/packages/backend/src/i18n/it.po new file mode 100644 index 0000000..6b35bd0 --- /dev/null +++ b/packages/backend/src/i18n/it.po @@ -0,0 +1,1057 @@ +# This file is part of TALER +# (C) 2016 GNUnet e.V. +# +# TALER is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# +# TALER is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# TALER; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "" + +#: src/InstanceRoutes.tsx:110 +#, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:289 +#, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "" + +#: src/components/form/InputDate.tsx:81 +#, c-format +msgid "clear" +msgstr "" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "" + +#: src/components/form/InputLocation.tsx:38 +#, c-format +msgid "Town location" +msgstr "" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:59 +#, c-format +msgid "Product id" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "" + +#: src/components/form/InputStock.tsx:105 +#, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, c-format +msgid "Orders" +msgstr "" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "" + +#: src/components/menu/SideBar.tsx:87 +#, c-format +msgid "Connection" +msgstr "" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "" + +#: src/components/menu/SideBar.tsx:116 +#, c-format +msgid "New" +msgstr "" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, c-format +msgid "Delete" +msgstr "" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, c-format +msgid "Net" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, c-format +msgid "Location" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, c-format +msgid "should be greater than 0" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, c-format +msgid "Order status" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, c-format +msgid "Product list" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, c-format +msgid "could not create the refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:108 +#, c-format +msgid "Refunded" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:109 +#, c-format +msgid "Not wired" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, c-format +msgid "Transfer ID" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, c-format +msgid "Account Address" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, c-format +msgid "could not inform transfer" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, c-format +msgid "load newer transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, c-format +msgid "Confirmed" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, c-format +msgid "Executed at" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, c-format +msgid "load older transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "" diff --git a/packages/backend/src/i18n/poheader b/packages/backend/src/i18n/poheader new file mode 100644 index 0000000..ee3fcd7 --- /dev/null +++ b/packages/backend/src/i18n/poheader @@ -0,0 +1,27 @@ +# This file is part of GNU Taler +# (C) 2021 Taler Systems S.A. + +# GNU Taler is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. + +# GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. + +# You should have received a copy of the GNU General Public License along with +# GNU Taler; see the file COPYING. If not, see + +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: taler@gnu.org\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" diff --git a/packages/backend/src/i18n/strings-prelude b/packages/backend/src/i18n/strings-prelude new file mode 100644 index 0000000..cca13af --- /dev/null +++ b/packages/backend/src/i18n/strings-prelude @@ -0,0 +1,19 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/*eslint quote-props: ["error", "consistent"]*/ +export const strings: {[s: string]: any} = {}; + diff --git a/packages/backend/src/i18n/strings.ts b/packages/backend/src/i18n/strings.ts new file mode 100644 index 0000000..63e9694 --- /dev/null +++ b/packages/backend/src/i18n/strings.ts @@ -0,0 +1,3445 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/*eslint quote-props: ["error", "consistent"]*/ +export const strings: {[s: string]: any} = {}; + +strings['de'] = { + "domain": "messages", + "locale_data": { + "messages": { + "": { + "domain": "messages", + "plural_forms": "nplurals=2; plural=(n != 1);", + "lang": "" + }, + "Access denied": [ + "" + ], + "Check your token is valid": [ + "" + ], + "Couldn't access the server.": [ + "" + ], + "Could not infer instance id from url %1$s": [ + "" + ], + "HTTP status #%1$s: Server reported a problem": [ + "" + ], + "Got message: \"%1$s\" from: %2$s": [ + "" + ], + "No default instance": [ + "" + ], + "in order to use merchant backoffice, you should create the default instance": [ + "" + ], + "Server reported a problem: HTTP status #%1$s": [ + "" + ], + "Got message: %1$s from: %2$s": [ + "" + ], + "Login required": [ + "" + ], + "Please enter your auth token. Token should have \"secret-token:\" and start with Bearer or ApiKey": [ + "" + ], + "Confirm": [ + "" + ], + "The value %1$s is invalid for a payment url": [ + "" + ], + "pick a date": [ + "" + ], + "clear": [ + "" + ], + "never": [ + "" + ], + "Image should be smaller than 1 MB": [ + "" + ], + "Country": [ + "" + ], + "Address": [ + "" + ], + "Building number": [ + "" + ], + "Building name": [ + "" + ], + "Street": [ + "" + ], + "Post code": [ + "" + ], + "Town location": [ + "" + ], + "Town": [ + "" + ], + "District": [ + "" + ], + "Country subdivision": [ + "" + ], + "Product id": [ + "" + ], + "Description": [ + "" + ], + "Name": [ + "" + ], + "loading...": [ + "" + ], + "no products found": [ + "" + ], + "no results": [ + "" + ], + "Deleting": [ + "" + ], + "Changing": [ + "" + ], + "Manage token": [ + "" + ], + "Update": [ + "" + ], + "Remove": [ + "" + ], + "Cancel": [ + "" + ], + "Manage stock": [ + "" + ], + "Infinite": [ + "" + ], + "lost cannot be greater that current + incoming (max %1$s)": [ + "" + ], + "current stock will change from %1$s to %2$s": [ + "" + ], + "current stock will stay at %1$s": [ + "" + ], + "Incoming": [ + "" + ], + "Lost": [ + "" + ], + "Current": [ + "" + ], + "without stock": [ + "" + ], + "Next restock": [ + "" + ], + "Delivery address": [ + "" + ], + "this product has no taxes": [ + "" + ], + "Amount": [ + "" + ], + "currency and value separated with colon": [ + "" + ], + "Add": [ + "" + ], + "Instance": [ + "" + ], + "Settings": [ + "" + ], + "Orders": [ + "" + ], + "Products": [ + "" + ], + "Transfers": [ + "" + ], + "Connection": [ + "" + ], + "Instances": [ + "" + ], + "New": [ + "" + ], + "List": [ + "" + ], + "Log out": [ + "" + ], + "Clear": [ + "" + ], + "should be the same": [ + "" + ], + "cannot be the same as before": [ + "" + ], + "You are updating the authorization token from instance %1$s with id %2$s": [ + "" + ], + "Old token": [ + "" + ], + "New token": [ + "" + ], + "Clearing the auth token will mean public access to the instance": [ + "" + ], + "ID": [ + "" + ], + "Image": [ + "" + ], + "Unit": [ + "" + ], + "Price": [ + "" + ], + "Stock": [ + "" + ], + "Taxes": [ + "" + ], + "Server not found": [ + "" + ], + "Couldn't access the server": [ + "" + ], + "Got message %1$s from %2$s": [ + "" + ], + "Unexpected Error": [ + "" + ], + "Auth token": [ + "" + ], + "Account address": [ + "" + ], + "Default max deposit fee": [ + "" + ], + "Default max wire fee": [ + "" + ], + "Default wire fee amortization": [ + "" + ], + "Jurisdiction": [ + "" + ], + "Default pay delay": [ + "" + ], + "Default wire transfer delay": [ + "" + ], + "could not create instance": [ + "" + ], + "Delete": [ + "" + ], + "Edit": [ + "" + ], + "There is no instances yet, add more pressing the + sign": [ + "" + ], + "Inventory products": [ + "" + ], + "Total price": [ + "" + ], + "Total tax": [ + "" + ], + "Order price": [ + "" + ], + "Net": [ + "" + ], + "Summary": [ + "" + ], + "Payments options": [ + "" + ], + "Auto refund deadline": [ + "" + ], + "Refund deadline": [ + "" + ], + "Pay deadline": [ + "" + ], + "Delivery date": [ + "" + ], + "Location": [ + "" + ], + "Max fee": [ + "" + ], + "Max wire fee": [ + "" + ], + "Wire fee amortization": [ + "" + ], + "Fullfilment url": [ + "" + ], + "Extra information": [ + "" + ], + "select a product first": [ + "" + ], + "should be greater than 0": [ + "" + ], + "cannot be greater than current stock and quantity previously added. max: %1$s": [ + "" + ], + "cannot be greater than current stock %1$s": [ + "" + ], + "Quantity": [ + "" + ], + "Order": [ + "" + ], + "claimed": [ + "" + ], + "copy url": [ + "" + ], + "pay at": [ + "" + ], + "created at": [ + "" + ], + "Timeline": [ + "" + ], + "Payment details": [ + "" + ], + "Order status": [ + "" + ], + "Product list": [ + "" + ], + "paid": [ + "" + ], + "wired": [ + "" + ], + "refunded": [ + "" + ], + "refund": [ + "" + ], + "Refunded amount": [ + "" + ], + "Deposit total": [ + "" + ], + "unpaid": [ + "" + ], + "Order status URL": [ + "" + ], + "Pay URI": [ + "" + ], + "Unknown order status. This is an error, please contact the administrator.": [ + "" + ], + "refund created successfully": [ + "" + ], + "could not create the refund": [ + "" + ], + "load newer orders": [ + "" + ], + "Date": [ + "" + ], + "Refund": [ + "" + ], + "load older orders": [ + "" + ], + "No orders has been found": [ + "" + ], + "date": [ + "" + ], + "amount": [ + "" + ], + "reason": [ + "" + ], + "Max refundable:": [ + "" + ], + "Reason": [ + "" + ], + "duplicated": [ + "" + ], + "requested by the customer": [ + "" + ], + "other": [ + "" + ], + "go to order id": [ + "" + ], + "Paid": [ + "" + ], + "Refunded": [ + "" + ], + "Not wired": [ + "" + ], + "All": [ + "" + ], + "could not create product": [ + "" + ], + "Sell": [ + "" + ], + "Profit": [ + "" + ], + "Sold": [ + "" + ], + "product updated successfully": [ + "" + ], + "could not update the product": [ + "" + ], + "product delete successfully": [ + "" + ], + "could not delete the product": [ + "" + ], + "Tips": [ + "" + ], + "Committed amount": [ + "" + ], + "Exchange initial amount": [ + "" + ], + "Merchant initial amount": [ + "" + ], + "There is no tips yet, add more pressing the + sign": [ + "" + ], + "cannot be empty": [ + "" + ], + "check the id, doest look valid": [ + "" + ], + "should have 52 characters, current %1$s": [ + "" + ], + "URL doesn't have the right format": [ + "" + ], + "Transfer ID": [ + "" + ], + "Account Address": [ + "" + ], + "Exchange URL": [ + "" + ], + "could not inform transfer": [ + "" + ], + "load newer transfers": [ + "" + ], + "Credit": [ + "" + ], + "Confirmed": [ + "" + ], + "Verified": [ + "" + ], + "Executed at": [ + "" + ], + "yes": [ + "" + ], + "no": [ + "" + ], + "unknown": [ + "" + ], + "load older transfers": [ + "" + ], + "There is no transfer yet, add more pressing the + sign": [ + "" + ] + } + } +}; + +strings['en'] = { + "domain": "messages", + "locale_data": { + "messages": { + "": { + "domain": "messages", + "plural_forms": "nplurals=2; plural=(n != 1);", + "lang": "" + }, + "Access denied": [ + "" + ], + "Check your token is valid": [ + "" + ], + "Couldn't access the server.": [ + "" + ], + "Could not infer instance id from url %1$s": [ + "" + ], + "HTTP status #%1$s: Server reported a problem": [ + "" + ], + "Got message: \"%1$s\" from: %2$s": [ + "" + ], + "No default instance": [ + "" + ], + "in order to use merchant backoffice, you should create the default instance": [ + "" + ], + "Server reported a problem: HTTP status #%1$s": [ + "" + ], + "Got message: %1$s from: %2$s": [ + "" + ], + "Login required": [ + "" + ], + "Please enter your auth token. Token should have \"secret-token:\" and start with Bearer or ApiKey": [ + "" + ], + "Confirm": [ + "" + ], + "The value %1$s is invalid for a payment url": [ + "" + ], + "pick a date": [ + "" + ], + "clear": [ + "" + ], + "never": [ + "" + ], + "Image should be smaller than 1 MB": [ + "" + ], + "Country": [ + "" + ], + "Address": [ + "" + ], + "Building number": [ + "" + ], + "Building name": [ + "" + ], + "Street": [ + "" + ], + "Post code": [ + "" + ], + "Town location": [ + "" + ], + "Town": [ + "" + ], + "District": [ + "" + ], + "Country subdivision": [ + "" + ], + "Product id": [ + "" + ], + "Description": [ + "" + ], + "Name": [ + "" + ], + "loading...": [ + "" + ], + "no products found": [ + "" + ], + "no results": [ + "" + ], + "Deleting": [ + "" + ], + "Changing": [ + "" + ], + "Manage token": [ + "" + ], + "Update": [ + "" + ], + "Remove": [ + "" + ], + "Cancel": [ + "" + ], + "Manage stock": [ + "" + ], + "Infinite": [ + "" + ], + "lost cannot be greater that current + incoming (max %1$s)": [ + "" + ], + "current stock will change from %1$s to %2$s": [ + "" + ], + "current stock will stay at %1$s": [ + "" + ], + "Incoming": [ + "" + ], + "Lost": [ + "" + ], + "Current": [ + "" + ], + "without stock": [ + "" + ], + "Next restock": [ + "" + ], + "Delivery address": [ + "" + ], + "this product has no taxes": [ + "" + ], + "Amount": [ + "" + ], + "currency and value separated with colon": [ + "" + ], + "Add": [ + "" + ], + "Instance": [ + "" + ], + "Settings": [ + "" + ], + "Orders": [ + "" + ], + "Products": [ + "" + ], + "Transfers": [ + "" + ], + "Connection": [ + "" + ], + "Instances": [ + "" + ], + "New": [ + "" + ], + "List": [ + "" + ], + "Log out": [ + "" + ], + "Clear": [ + "" + ], + "should be the same": [ + "" + ], + "cannot be the same as before": [ + "" + ], + "You are updating the authorization token from instance %1$s with id %2$s": [ + "" + ], + "Old token": [ + "" + ], + "New token": [ + "" + ], + "Clearing the auth token will mean public access to the instance": [ + "" + ], + "ID": [ + "" + ], + "Image": [ + "" + ], + "Unit": [ + "" + ], + "Price": [ + "" + ], + "Stock": [ + "" + ], + "Taxes": [ + "" + ], + "Server not found": [ + "" + ], + "Couldn't access the server": [ + "" + ], + "Got message %1$s from %2$s": [ + "" + ], + "Unexpected Error": [ + "" + ], + "Auth token": [ + "" + ], + "Account address": [ + "" + ], + "Default max deposit fee": [ + "" + ], + "Default max wire fee": [ + "" + ], + "Default wire fee amortization": [ + "" + ], + "Jurisdiction": [ + "" + ], + "Default pay delay": [ + "" + ], + "Default wire transfer delay": [ + "" + ], + "could not create instance": [ + "" + ], + "Delete": [ + "" + ], + "Edit": [ + "" + ], + "There is no instances yet, add more pressing the + sign": [ + "" + ], + "Inventory products": [ + "" + ], + "Total price": [ + "" + ], + "Total tax": [ + "" + ], + "Order price": [ + "" + ], + "Net": [ + "" + ], + "Summary": [ + "" + ], + "Payments options": [ + "" + ], + "Auto refund deadline": [ + "" + ], + "Refund deadline": [ + "" + ], + "Pay deadline": [ + "" + ], + "Delivery date": [ + "" + ], + "Location": [ + "" + ], + "Max fee": [ + "" + ], + "Max wire fee": [ + "" + ], + "Wire fee amortization": [ + "" + ], + "Fullfilment url": [ + "" + ], + "Extra information": [ + "" + ], + "select a product first": [ + "" + ], + "should be greater than 0": [ + "" + ], + "cannot be greater than current stock and quantity previously added. max: %1$s": [ + "" + ], + "cannot be greater than current stock %1$s": [ + "" + ], + "Quantity": [ + "" + ], + "Order": [ + "" + ], + "claimed": [ + "" + ], + "copy url": [ + "" + ], + "pay at": [ + "" + ], + "created at": [ + "" + ], + "Timeline": [ + "" + ], + "Payment details": [ + "" + ], + "Order status": [ + "" + ], + "Product list": [ + "" + ], + "paid": [ + "" + ], + "wired": [ + "" + ], + "refunded": [ + "" + ], + "refund": [ + "" + ], + "Refunded amount": [ + "" + ], + "Deposit total": [ + "" + ], + "unpaid": [ + "" + ], + "Order status URL": [ + "" + ], + "Pay URI": [ + "" + ], + "Unknown order status. This is an error, please contact the administrator.": [ + "" + ], + "refund created successfully": [ + "" + ], + "could not create the refund": [ + "" + ], + "load newer orders": [ + "" + ], + "Date": [ + "" + ], + "Refund": [ + "" + ], + "load older orders": [ + "" + ], + "No orders has been found": [ + "" + ], + "date": [ + "" + ], + "amount": [ + "" + ], + "reason": [ + "" + ], + "Max refundable:": [ + "" + ], + "Reason": [ + "" + ], + "duplicated": [ + "" + ], + "requested by the customer": [ + "" + ], + "other": [ + "" + ], + "go to order id": [ + "" + ], + "Paid": [ + "" + ], + "Refunded": [ + "" + ], + "Not wired": [ + "" + ], + "All": [ + "" + ], + "could not create product": [ + "" + ], + "Sell": [ + "" + ], + "Profit": [ + "" + ], + "Sold": [ + "" + ], + "product updated successfully": [ + "" + ], + "could not update the product": [ + "" + ], + "product delete successfully": [ + "" + ], + "could not delete the product": [ + "" + ], + "Tips": [ + "" + ], + "Committed amount": [ + "" + ], + "Exchange initial amount": [ + "" + ], + "Merchant initial amount": [ + "" + ], + "There is no tips yet, add more pressing the + sign": [ + "" + ], + "cannot be empty": [ + "" + ], + "check the id, doest look valid": [ + "" + ], + "should have 52 characters, current %1$s": [ + "" + ], + "URL doesn't have the right format": [ + "" + ], + "Transfer ID": [ + "" + ], + "Account Address": [ + "" + ], + "Exchange URL": [ + "" + ], + "could not inform transfer": [ + "" + ], + "load newer transfers": [ + "" + ], + "Credit": [ + "" + ], + "Confirmed": [ + "" + ], + "Verified": [ + "" + ], + "Executed at": [ + "" + ], + "yes": [ + "" + ], + "no": [ + "" + ], + "unknown": [ + "" + ], + "load older transfers": [ + "" + ], + "There is no transfer yet, add more pressing the + sign": [ + "" + ] + } + } +}; + +strings['es'] = { + "domain": "messages", + "locale_data": { + "messages": { + "": { + "domain": "messages", + "plural_forms": "nplurals=2; plural=(n != 1);", + "lang": "" + }, + "Access denied": [ + "Acceso denegado" + ], + "Check your token is valid": [ + "Verifica que el token sea valido" + ], + "Couldn't access the server.": [ + "No se pudo acceder al servidor" + ], + "Could not infer instance id from url %1$s": [ + "No se pudo inferir el id de la instancia con la url %1$s" + ], + "HTTP status #%1$s: Server reported a problem": [ + "HTTP status #%1$s: Servidor reporto un problema" + ], + "Got message: \"%1$s\" from: %2$s": [ + "Recivimos el mensaje %1$s desde %2$s" + ], + "No default instance": [ + "Sin instancia default" + ], + "in order to use merchant backoffice, you should create the default instance": [ + "para usar el merchant backoffice, deberΓ­a crear la instancia default" + ], + "Server reported a problem: HTTP status #%1$s": [ + "Servidir reporto un problema: HTTP status #%1$s" + ], + "Got message: %1$s from: %2$s": [ + "Recivimos el mensaje %1$s desde %2$s" + ], + "Login required": [ + "Login necesario" + ], + "Please enter your auth token. Token should have \"secret-token:\" and start with Bearer or ApiKey": [ + "Por favor ingrese su token de autorizaciΓ³n. El token debe tener \"secret-token\" y comenzar con Bearer o ApiKey" + ], + "Confirm": [ + "Confirmar" + ], + "The value %1$s is invalid for a payment url": [ + "El valor %1$s es invalido para una URL de pago" + ], + "pick a date": [ + "elegir una fecha" + ], + "clear": [ + "Limpiar" + ], + "never": [ + "nunca" + ], + "Image should be smaller than 1 MB": [ + "La imagen debe ser mas chica que 1 MB" + ], + "Country": [ + "PaΓ­s" + ], + "Address": [ + "DirecciΓ³n" + ], + "Building number": [ + "NΓΊmero de edificio" + ], + "Building name": [ + "Nombre de edificio" + ], + "Street": [ + "Calle" + ], + "Post code": [ + "CΓ³digo postal" + ], + "Town location": [ + "UbicaciΓ³n de ciudad" + ], + "Town": [ + "Ciudad" + ], + "District": [ + "Distrito" + ], + "Country subdivision": [ + "Provincia" + ], + "Product id": [ + "Id de producto" + ], + "Description": [ + "Descripcion" + ], + "Name": [ + "Nombre" + ], + "loading...": [ + "Cargando..." + ], + "no products found": [ + "No se encontraron productos" + ], + "no results": [ + "Sin resultados" + ], + "Deleting": [ + "Borrando" + ], + "Changing": [ + "Cambiando" + ], + "Manage token": [ + "Administrar token" + ], + "Update": [ + "Actualizar" + ], + "Remove": [ + "Eliminar" + ], + "Cancel": [ + "Cancelar" + ], + "Manage stock": [ + "Administrar stock" + ], + "Infinite": [ + "Inifinito" + ], + "lost cannot be greater that current + incoming (max %1$s)": [ + "no puede ser mayor al stock actual %1$s" + ], + "current stock will change from %1$s to %2$s": [ + "stock actual cambiarΓ‘ desde %1$s a %2$s" + ], + "current stock will stay at %1$s": [ + "stock actual seguirΓ‘ en %1$s" + ], + "Incoming": [ + "Ingresando" + ], + "Lost": [ + "Perdido" + ], + "Current": [ + "Actual" + ], + "without stock": [ + "sin stock" + ], + "Next restock": [ + "PrΓ³ximo reabastecimiento" + ], + "Delivery address": [ + "DirecciΓ³n de entrega" + ], + "this product has no taxes": [ + "este producto no tiene impuestos" + ], + "Amount": [ + "Monto" + ], + "currency and value separated with colon": [ + "Moneda y valor separado por dos puntos" + ], + "Add": [ + "Agregar" + ], + "Instance": [ + "Instancia" + ], + "Settings": [ + "ConfiguraciΓ³n" + ], + "Orders": [ + "Ordenes" + ], + "Products": [ + "Productos" + ], + "Transfers": [ + "Transferencias" + ], + "Connection": [ + "ConexiΓ³n" + ], + "Instances": [ + "Instancias" + ], + "New": [ + "Nuevo" + ], + "List": [ + "Lista" + ], + "Log out": [ + "Salir" + ], + "Clear": [ + "Limpiar" + ], + "should be the same": [ + "deberΓ­an ser iguales" + ], + "cannot be the same as before": [ + "no puede ser igual al anterior" + ], + "You are updating the authorization token from instance %1$s with id %2$s": [ + "EstΓ‘ actualizando el token de autorizaciΓ³n para la instancia %1$s con id %2$s" + ], + "Old token": [ + "Viejo token" + ], + "New token": [ + "Nuevo token" + ], + "Clearing the auth token will mean public access to the instance": [ + "Limpiar el token de autorizaciΓ³n significa acceso publico a la instancia" + ], + "ID": [ + "ID" + ], + "Image": [ + "Imagen" + ], + "Unit": [ + "Unidad" + ], + "Price": [ + "Precio" + ], + "Stock": [ + "Stock" + ], + "Taxes": [ + "Impuesto" + ], + "Server not found": [ + "Servidor no encontrado" + ], + "Couldn't access the server": [ + "No se pudo aceder al servidor" + ], + "Got message %1$s from %2$s": [ + "Recivimos el mensaje %1$s desde %2$s" + ], + "Unexpected Error": [ + "Error inesperado" + ], + "Auth token": [ + "Token de autorizaciΓ³n" + ], + "Account address": [ + "DirecciΓ³n de cuenta" + ], + "Default max deposit fee": [ + "Impuesto mΓ‘ximo de deposito por omisiΓ³n" + ], + "Default max wire fee": [ + "Impuesto mΓ‘ximo de transferencia por omisiΓ³n" + ], + "Default wire fee amortization": [ + "AmortizaciΓ³n de impuesto de transferencia por omisiΓ³n" + ], + "Jurisdiction": [ + "JurisdicciΓ³n" + ], + "Default pay delay": [ + "Retrazo de pago por omisiΓ³n" + ], + "Default wire transfer delay": [ + "Retrazo de transferencia por omisiΓ³n" + ], + "could not create instance": [ + "no se pudo crear la instancia" + ], + "Delete": [ + "Borrando" + ], + "Edit": [ + "" + ], + "There is no instances yet, add more pressing the + sign": [ + "No hay instancias todavΓ­an, agregue mas presionando el signo +" + ], + "Inventory products": [ + "Productos de inventario" + ], + "Total price": [ + "Precio total" + ], + "Total tax": [ + "Impuesto total" + ], + "Order price": [ + "Precio de la orden" + ], + "Net": [ + "Neto" + ], + "Summary": [ + "Resumen" + ], + "Payments options": [ + "Opciones de pago" + ], + "Auto refund deadline": [ + "Plazo de reembolso automΓ‘tico" + ], + "Refund deadline": [ + "Plazo de reembolso" + ], + "Pay deadline": [ + "Plazo de pago" + ], + "Delivery date": [ + "Fecha de entrega" + ], + "Location": [ + "UbicaciΓ³n" + ], + "Max fee": [ + "Impuesto mΓ‘ximo" + ], + "Max wire fee": [ + "Impuesto de transferencia mΓ‘ximo" + ], + "Wire fee amortization": [ + "AmortizaciΓ³n de impuesto de transferencia" + ], + "Fullfilment url": [ + "URL de completitud" + ], + "Extra information": [ + "InformaciΓ³n extra" + ], + "select a product first": [ + "seleccione un producto primero" + ], + "should be greater than 0": [ + "La imagen debe ser mas chica que 1 MB" + ], + "cannot be greater than current stock and quantity previously added. max: %1$s": [ + "no puede ser mayor al stock actual y la cantidad previamente agregada. mΓ‘ximo: %1$s" + ], + "cannot be greater than current stock %1$s": [ + "no puede ser mayor al stock actual %1$s" + ], + "Quantity": [ + "Cantidad" + ], + "Order": [ + "Orden" + ], + "claimed": [ + "reclamado" + ], + "copy url": [ + "copiar url" + ], + "pay at": [ + "pagar en" + ], + "created at": [ + "creado" + ], + "Timeline": [ + "CronologΓ­a" + ], + "Payment details": [ + "Detalles de pago" + ], + "Order status": [ + "Estado de orden" + ], + "Product list": [ + "Lista de producto" + ], + "paid": [ + "pagados" + ], + "wired": [ + "transferido" + ], + "refunded": [ + "reembolzado" + ], + "refund": [ + "reembolzar" + ], + "Refunded amount": [ + "Monto reembolzado" + ], + "Deposit total": [ + "Total depositado" + ], + "unpaid": [ + "impago" + ], + "Order status URL": [ + "URL de estado de orden" + ], + "Pay URI": [ + "URI de pago" + ], + "Unknown order status. This is an error, please contact the administrator.": [ + "Estado de orden desconocido. Esto es un error, por favor contacte a su administrador" + ], + "refund created successfully": [ + "reembolzo creado satisfactoriamente" + ], + "could not create the refund": [ + "No se pudo aceder al servidor" + ], + "load newer orders": [ + "cargar nuevas ordenes" + ], + "Date": [ + "Fecha" + ], + "Refund": [ + "Reembolzar" + ], + "load older orders": [ + "cargar viejas ordenes" + ], + "No orders has been found": [ + "No se enconraron ordenes" + ], + "date": [ + "fecha" + ], + "amount": [ + "monto" + ], + "reason": [ + "razΓ³n" + ], + "Max refundable:": [ + "MΓ‘ximo reembolzable:" + ], + "Reason": [ + "RazΓ³n" + ], + "duplicated": [ + "duplicado" + ], + "requested by the customer": [ + "pedido por el consumidor" + ], + "other": [ + "otro" + ], + "go to order id": [ + "ir a id de orden" + ], + "Paid": [ + "Pagado" + ], + "Refunded": [ + "Reembolzado" + ], + "Not wired": [ + "No transferido" + ], + "All": [ + "Todo" + ], + "could not create product": [ + "no se pudo crear el producto" + ], + "Sell": [ + "Venta" + ], + "Profit": [ + "Ganancia" + ], + "Sold": [ + "Vendido" + ], + "product updated successfully": [ + "producto actualizado correctamente" + ], + "could not update the product": [ + "no se pudo actualizar el producto" + ], + "product delete successfully": [ + "producto fue eliminado correctamente" + ], + "could not delete the product": [ + "no se pudo eliminar el producto" + ], + "Tips": [ + "Propinas" + ], + "Committed amount": [ + "" + ], + "Exchange initial amount": [ + "" + ], + "Merchant initial amount": [ + "" + ], + "There is no tips yet, add more pressing the + sign": [ + "No hay propinas todavΓ­a, agregar mas presionando el signo +" + ], + "cannot be empty": [ + "no puede ser vacΓ­o" + ], + "check the id, doest look valid": [ + "verificar el id, no parece vΓ‘lido" + ], + "should have 52 characters, current %1$s": [ + "deberΓ­a tener 52 caracteres, actualmente %1$s" + ], + "URL doesn't have the right format": [ + "La URL no tiene el formato correcto" + ], + "Transfer ID": [ + "Transferencias" + ], + "Account Address": [ + "DirecciΓ³n de cuenta" + ], + "Exchange URL": [ + "URL del Exchange" + ], + "could not inform transfer": [ + "no se pudo crear la instancia" + ], + "load newer transfers": [ + "cargar nuevas ordenes" + ], + "Credit": [ + "CrΓ©dito" + ], + "Confirmed": [ + "Confirmar" + ], + "Verified": [ + "Verificado" + ], + "Executed at": [ + "creado" + ], + "yes": [ + "si" + ], + "no": [ + "no" + ], + "unknown": [ + "desconocido" + ], + "load older transfers": [ + "cargar viejas transferencias" + ], + "There is no transfer yet, add more pressing the + sign": [ + "No hay transferencias todavΓ­a, agregar mas presionando el signo +" + ] + } + } +}; + +strings['fr'] = { + "domain": "messages", + "locale_data": { + "messages": { + "": { + "domain": "messages", + "plural_forms": "nplurals=2; plural=(n != 1);", + "lang": "" + }, + "Access denied": [ + "" + ], + "Check your token is valid": [ + "" + ], + "Couldn't access the server.": [ + "" + ], + "Could not infer instance id from url %1$s": [ + "" + ], + "HTTP status #%1$s: Server reported a problem": [ + "" + ], + "Got message: \"%1$s\" from: %2$s": [ + "" + ], + "No default instance": [ + "" + ], + "in order to use merchant backoffice, you should create the default instance": [ + "" + ], + "Server reported a problem: HTTP status #%1$s": [ + "" + ], + "Got message: %1$s from: %2$s": [ + "" + ], + "Login required": [ + "" + ], + "Please enter your auth token. Token should have \"secret-token:\" and start with Bearer or ApiKey": [ + "" + ], + "Confirm": [ + "" + ], + "The value %1$s is invalid for a payment url": [ + "" + ], + "pick a date": [ + "" + ], + "clear": [ + "" + ], + "never": [ + "" + ], + "Image should be smaller than 1 MB": [ + "" + ], + "Country": [ + "" + ], + "Address": [ + "" + ], + "Building number": [ + "" + ], + "Building name": [ + "" + ], + "Street": [ + "" + ], + "Post code": [ + "" + ], + "Town location": [ + "" + ], + "Town": [ + "" + ], + "District": [ + "" + ], + "Country subdivision": [ + "" + ], + "Product id": [ + "" + ], + "Description": [ + "" + ], + "Name": [ + "" + ], + "loading...": [ + "" + ], + "no products found": [ + "" + ], + "no results": [ + "" + ], + "Deleting": [ + "" + ], + "Changing": [ + "" + ], + "Manage token": [ + "" + ], + "Update": [ + "" + ], + "Remove": [ + "" + ], + "Cancel": [ + "" + ], + "Manage stock": [ + "" + ], + "Infinite": [ + "" + ], + "lost cannot be greater that current + incoming (max %1$s)": [ + "" + ], + "current stock will change from %1$s to %2$s": [ + "" + ], + "current stock will stay at %1$s": [ + "" + ], + "Incoming": [ + "" + ], + "Lost": [ + "" + ], + "Current": [ + "" + ], + "without stock": [ + "" + ], + "Next restock": [ + "" + ], + "Delivery address": [ + "" + ], + "this product has no taxes": [ + "" + ], + "Amount": [ + "" + ], + "currency and value separated with colon": [ + "" + ], + "Add": [ + "" + ], + "Instance": [ + "" + ], + "Settings": [ + "" + ], + "Orders": [ + "" + ], + "Products": [ + "" + ], + "Transfers": [ + "" + ], + "Connection": [ + "" + ], + "Instances": [ + "" + ], + "New": [ + "" + ], + "List": [ + "" + ], + "Log out": [ + "" + ], + "Clear": [ + "" + ], + "should be the same": [ + "" + ], + "cannot be the same as before": [ + "" + ], + "You are updating the authorization token from instance %1$s with id %2$s": [ + "" + ], + "Old token": [ + "" + ], + "New token": [ + "" + ], + "Clearing the auth token will mean public access to the instance": [ + "" + ], + "ID": [ + "" + ], + "Image": [ + "" + ], + "Unit": [ + "" + ], + "Price": [ + "" + ], + "Stock": [ + "" + ], + "Taxes": [ + "" + ], + "Server not found": [ + "" + ], + "Couldn't access the server": [ + "" + ], + "Got message %1$s from %2$s": [ + "" + ], + "Unexpected Error": [ + "" + ], + "Auth token": [ + "" + ], + "Account address": [ + "" + ], + "Default max deposit fee": [ + "" + ], + "Default max wire fee": [ + "" + ], + "Default wire fee amortization": [ + "" + ], + "Jurisdiction": [ + "" + ], + "Default pay delay": [ + "" + ], + "Default wire transfer delay": [ + "" + ], + "could not create instance": [ + "" + ], + "Delete": [ + "" + ], + "Edit": [ + "" + ], + "There is no instances yet, add more pressing the + sign": [ + "" + ], + "Inventory products": [ + "" + ], + "Total price": [ + "" + ], + "Total tax": [ + "" + ], + "Order price": [ + "" + ], + "Net": [ + "" + ], + "Summary": [ + "" + ], + "Payments options": [ + "" + ], + "Auto refund deadline": [ + "" + ], + "Refund deadline": [ + "" + ], + "Pay deadline": [ + "" + ], + "Delivery date": [ + "" + ], + "Location": [ + "" + ], + "Max fee": [ + "" + ], + "Max wire fee": [ + "" + ], + "Wire fee amortization": [ + "" + ], + "Fullfilment url": [ + "" + ], + "Extra information": [ + "" + ], + "select a product first": [ + "" + ], + "should be greater than 0": [ + "" + ], + "cannot be greater than current stock and quantity previously added. max: %1$s": [ + "" + ], + "cannot be greater than current stock %1$s": [ + "" + ], + "Quantity": [ + "" + ], + "Order": [ + "" + ], + "claimed": [ + "" + ], + "copy url": [ + "" + ], + "pay at": [ + "" + ], + "created at": [ + "" + ], + "Timeline": [ + "" + ], + "Payment details": [ + "" + ], + "Order status": [ + "" + ], + "Product list": [ + "" + ], + "paid": [ + "" + ], + "wired": [ + "" + ], + "refunded": [ + "" + ], + "refund": [ + "" + ], + "Refunded amount": [ + "" + ], + "Deposit total": [ + "" + ], + "unpaid": [ + "" + ], + "Order status URL": [ + "" + ], + "Pay URI": [ + "" + ], + "Unknown order status. This is an error, please contact the administrator.": [ + "" + ], + "refund created successfully": [ + "" + ], + "could not create the refund": [ + "" + ], + "load newer orders": [ + "" + ], + "Date": [ + "" + ], + "Refund": [ + "" + ], + "load older orders": [ + "" + ], + "No orders has been found": [ + "" + ], + "date": [ + "" + ], + "amount": [ + "" + ], + "reason": [ + "" + ], + "Max refundable:": [ + "" + ], + "Reason": [ + "" + ], + "duplicated": [ + "" + ], + "requested by the customer": [ + "" + ], + "other": [ + "" + ], + "go to order id": [ + "" + ], + "Paid": [ + "" + ], + "Refunded": [ + "" + ], + "Not wired": [ + "" + ], + "All": [ + "" + ], + "could not create product": [ + "" + ], + "Sell": [ + "" + ], + "Profit": [ + "" + ], + "Sold": [ + "" + ], + "product updated successfully": [ + "" + ], + "could not update the product": [ + "" + ], + "product delete successfully": [ + "" + ], + "could not delete the product": [ + "" + ], + "Tips": [ + "" + ], + "Committed amount": [ + "" + ], + "Exchange initial amount": [ + "" + ], + "Merchant initial amount": [ + "" + ], + "There is no tips yet, add more pressing the + sign": [ + "" + ], + "cannot be empty": [ + "" + ], + "check the id, doest look valid": [ + "" + ], + "should have 52 characters, current %1$s": [ + "" + ], + "URL doesn't have the right format": [ + "" + ], + "Transfer ID": [ + "" + ], + "Account Address": [ + "" + ], + "Exchange URL": [ + "" + ], + "could not inform transfer": [ + "" + ], + "load newer transfers": [ + "" + ], + "Credit": [ + "" + ], + "Confirmed": [ + "" + ], + "Verified": [ + "" + ], + "Executed at": [ + "" + ], + "yes": [ + "" + ], + "no": [ + "" + ], + "unknown": [ + "" + ], + "load older transfers": [ + "" + ], + "There is no transfer yet, add more pressing the + sign": [ + "" + ] + } + } +}; + +strings['it'] = { + "domain": "messages", + "locale_data": { + "messages": { + "": { + "domain": "messages", + "plural_forms": "nplurals=2; plural=(n != 1);", + "lang": "" + }, + "Access denied": [ + "" + ], + "Check your token is valid": [ + "" + ], + "Couldn't access the server.": [ + "" + ], + "Could not infer instance id from url %1$s": [ + "" + ], + "HTTP status #%1$s: Server reported a problem": [ + "" + ], + "Got message: \"%1$s\" from: %2$s": [ + "" + ], + "No default instance": [ + "" + ], + "in order to use merchant backoffice, you should create the default instance": [ + "" + ], + "Server reported a problem: HTTP status #%1$s": [ + "" + ], + "Got message: %1$s from: %2$s": [ + "" + ], + "Login required": [ + "" + ], + "Please enter your auth token. Token should have \"secret-token:\" and start with Bearer or ApiKey": [ + "" + ], + "Confirm": [ + "" + ], + "The value %1$s is invalid for a payment url": [ + "" + ], + "pick a date": [ + "" + ], + "clear": [ + "" + ], + "never": [ + "" + ], + "Image should be smaller than 1 MB": [ + "" + ], + "Country": [ + "" + ], + "Address": [ + "" + ], + "Building number": [ + "" + ], + "Building name": [ + "" + ], + "Street": [ + "" + ], + "Post code": [ + "" + ], + "Town location": [ + "" + ], + "Town": [ + "" + ], + "District": [ + "" + ], + "Country subdivision": [ + "" + ], + "Product id": [ + "" + ], + "Description": [ + "" + ], + "Name": [ + "" + ], + "loading...": [ + "" + ], + "no products found": [ + "" + ], + "no results": [ + "" + ], + "Deleting": [ + "" + ], + "Changing": [ + "" + ], + "Manage token": [ + "" + ], + "Update": [ + "" + ], + "Remove": [ + "" + ], + "Cancel": [ + "" + ], + "Manage stock": [ + "" + ], + "Infinite": [ + "" + ], + "lost cannot be greater that current + incoming (max %1$s)": [ + "" + ], + "current stock will change from %1$s to %2$s": [ + "" + ], + "current stock will stay at %1$s": [ + "" + ], + "Incoming": [ + "" + ], + "Lost": [ + "" + ], + "Current": [ + "" + ], + "without stock": [ + "" + ], + "Next restock": [ + "" + ], + "Delivery address": [ + "" + ], + "this product has no taxes": [ + "" + ], + "Amount": [ + "" + ], + "currency and value separated with colon": [ + "" + ], + "Add": [ + "" + ], + "Instance": [ + "" + ], + "Settings": [ + "" + ], + "Orders": [ + "" + ], + "Products": [ + "" + ], + "Transfers": [ + "" + ], + "Connection": [ + "" + ], + "Instances": [ + "" + ], + "New": [ + "" + ], + "List": [ + "" + ], + "Log out": [ + "" + ], + "Clear": [ + "" + ], + "should be the same": [ + "" + ], + "cannot be the same as before": [ + "" + ], + "You are updating the authorization token from instance %1$s with id %2$s": [ + "" + ], + "Old token": [ + "" + ], + "New token": [ + "" + ], + "Clearing the auth token will mean public access to the instance": [ + "" + ], + "ID": [ + "" + ], + "Image": [ + "" + ], + "Unit": [ + "" + ], + "Price": [ + "" + ], + "Stock": [ + "" + ], + "Taxes": [ + "" + ], + "Server not found": [ + "" + ], + "Couldn't access the server": [ + "" + ], + "Got message %1$s from %2$s": [ + "" + ], + "Unexpected Error": [ + "" + ], + "Auth token": [ + "" + ], + "Account address": [ + "" + ], + "Default max deposit fee": [ + "" + ], + "Default max wire fee": [ + "" + ], + "Default wire fee amortization": [ + "" + ], + "Jurisdiction": [ + "" + ], + "Default pay delay": [ + "" + ], + "Default wire transfer delay": [ + "" + ], + "could not create instance": [ + "" + ], + "Delete": [ + "" + ], + "Edit": [ + "" + ], + "There is no instances yet, add more pressing the + sign": [ + "" + ], + "Inventory products": [ + "" + ], + "Total price": [ + "" + ], + "Total tax": [ + "" + ], + "Order price": [ + "" + ], + "Net": [ + "" + ], + "Summary": [ + "" + ], + "Payments options": [ + "" + ], + "Auto refund deadline": [ + "" + ], + "Refund deadline": [ + "" + ], + "Pay deadline": [ + "" + ], + "Delivery date": [ + "" + ], + "Location": [ + "" + ], + "Max fee": [ + "" + ], + "Max wire fee": [ + "" + ], + "Wire fee amortization": [ + "" + ], + "Fullfilment url": [ + "" + ], + "Extra information": [ + "" + ], + "select a product first": [ + "" + ], + "should be greater than 0": [ + "" + ], + "cannot be greater than current stock and quantity previously added. max: %1$s": [ + "" + ], + "cannot be greater than current stock %1$s": [ + "" + ], + "Quantity": [ + "" + ], + "Order": [ + "" + ], + "claimed": [ + "" + ], + "copy url": [ + "" + ], + "pay at": [ + "" + ], + "created at": [ + "" + ], + "Timeline": [ + "" + ], + "Payment details": [ + "" + ], + "Order status": [ + "" + ], + "Product list": [ + "" + ], + "paid": [ + "" + ], + "wired": [ + "" + ], + "refunded": [ + "" + ], + "refund": [ + "" + ], + "Refunded amount": [ + "" + ], + "Deposit total": [ + "" + ], + "unpaid": [ + "" + ], + "Order status URL": [ + "" + ], + "Pay URI": [ + "" + ], + "Unknown order status. This is an error, please contact the administrator.": [ + "" + ], + "refund created successfully": [ + "" + ], + "could not create the refund": [ + "" + ], + "load newer orders": [ + "" + ], + "Date": [ + "" + ], + "Refund": [ + "" + ], + "load older orders": [ + "" + ], + "No orders has been found": [ + "" + ], + "date": [ + "" + ], + "amount": [ + "" + ], + "reason": [ + "" + ], + "Max refundable:": [ + "" + ], + "Reason": [ + "" + ], + "duplicated": [ + "" + ], + "requested by the customer": [ + "" + ], + "other": [ + "" + ], + "go to order id": [ + "" + ], + "Paid": [ + "" + ], + "Refunded": [ + "" + ], + "Not wired": [ + "" + ], + "All": [ + "" + ], + "could not create product": [ + "" + ], + "Sell": [ + "" + ], + "Profit": [ + "" + ], + "Sold": [ + "" + ], + "product updated successfully": [ + "" + ], + "could not update the product": [ + "" + ], + "product delete successfully": [ + "" + ], + "could not delete the product": [ + "" + ], + "Tips": [ + "" + ], + "Committed amount": [ + "" + ], + "Exchange initial amount": [ + "" + ], + "Merchant initial amount": [ + "" + ], + "There is no tips yet, add more pressing the + sign": [ + "" + ], + "cannot be empty": [ + "" + ], + "check the id, doest look valid": [ + "" + ], + "should have 52 characters, current %1$s": [ + "" + ], + "URL doesn't have the right format": [ + "" + ], + "Transfer ID": [ + "" + ], + "Account Address": [ + "" + ], + "Exchange URL": [ + "" + ], + "could not inform transfer": [ + "" + ], + "load newer transfers": [ + "" + ], + "Credit": [ + "" + ], + "Confirmed": [ + "" + ], + "Verified": [ + "" + ], + "Executed at": [ + "" + ], + "yes": [ + "" + ], + "no": [ + "" + ], + "unknown": [ + "" + ], + "load older transfers": [ + "" + ], + "There is no transfer yet, add more pressing the + sign": [ + "" + ] + } + } +}; + +strings['sv'] = { + "domain": "messages", + "locale_data": { + "messages": { + "": { + "domain": "messages", + "plural_forms": "nplurals=2; plural=(n != 1);", + "lang": "" + }, + "Access denied": [ + "" + ], + "Check your token is valid": [ + "" + ], + "Couldn't access the server.": [ + "" + ], + "Could not infer instance id from url %1$s": [ + "" + ], + "HTTP status #%1$s: Server reported a problem": [ + "" + ], + "Got message: \"%1$s\" from: %2$s": [ + "" + ], + "No default instance": [ + "" + ], + "in order to use merchant backoffice, you should create the default instance": [ + "" + ], + "Server reported a problem: HTTP status #%1$s": [ + "" + ], + "Got message: %1$s from: %2$s": [ + "" + ], + "Login required": [ + "" + ], + "Please enter your auth token. Token should have \"secret-token:\" and start with Bearer or ApiKey": [ + "" + ], + "Confirm": [ + "" + ], + "The value %1$s is invalid for a payment url": [ + "" + ], + "pick a date": [ + "" + ], + "clear": [ + "" + ], + "never": [ + "" + ], + "Image should be smaller than 1 MB": [ + "" + ], + "Country": [ + "" + ], + "Address": [ + "" + ], + "Building number": [ + "" + ], + "Building name": [ + "" + ], + "Street": [ + "" + ], + "Post code": [ + "" + ], + "Town location": [ + "" + ], + "Town": [ + "" + ], + "District": [ + "" + ], + "Country subdivision": [ + "" + ], + "Product id": [ + "" + ], + "Description": [ + "" + ], + "Name": [ + "" + ], + "loading...": [ + "" + ], + "no products found": [ + "" + ], + "no results": [ + "" + ], + "Deleting": [ + "" + ], + "Changing": [ + "" + ], + "Manage token": [ + "" + ], + "Update": [ + "" + ], + "Remove": [ + "" + ], + "Cancel": [ + "" + ], + "Manage stock": [ + "" + ], + "Infinite": [ + "" + ], + "lost cannot be greater that current + incoming (max %1$s)": [ + "" + ], + "current stock will change from %1$s to %2$s": [ + "" + ], + "current stock will stay at %1$s": [ + "" + ], + "Incoming": [ + "" + ], + "Lost": [ + "" + ], + "Current": [ + "" + ], + "without stock": [ + "" + ], + "Next restock": [ + "" + ], + "Delivery address": [ + "" + ], + "this product has no taxes": [ + "" + ], + "Amount": [ + "" + ], + "currency and value separated with colon": [ + "" + ], + "Add": [ + "" + ], + "Instance": [ + "" + ], + "Settings": [ + "" + ], + "Orders": [ + "" + ], + "Products": [ + "" + ], + "Transfers": [ + "" + ], + "Connection": [ + "" + ], + "Instances": [ + "" + ], + "New": [ + "" + ], + "List": [ + "" + ], + "Log out": [ + "" + ], + "Clear": [ + "" + ], + "should be the same": [ + "" + ], + "cannot be the same as before": [ + "" + ], + "You are updating the authorization token from instance %1$s with id %2$s": [ + "" + ], + "Old token": [ + "" + ], + "New token": [ + "" + ], + "Clearing the auth token will mean public access to the instance": [ + "" + ], + "ID": [ + "" + ], + "Image": [ + "" + ], + "Unit": [ + "" + ], + "Price": [ + "" + ], + "Stock": [ + "" + ], + "Taxes": [ + "" + ], + "Server not found": [ + "" + ], + "Couldn't access the server": [ + "" + ], + "Got message %1$s from %2$s": [ + "" + ], + "Unexpected Error": [ + "" + ], + "Auth token": [ + "" + ], + "Account address": [ + "" + ], + "Default max deposit fee": [ + "" + ], + "Default max wire fee": [ + "" + ], + "Default wire fee amortization": [ + "" + ], + "Jurisdiction": [ + "" + ], + "Default pay delay": [ + "" + ], + "Default wire transfer delay": [ + "" + ], + "could not create instance": [ + "" + ], + "Delete": [ + "" + ], + "Edit": [ + "" + ], + "There is no instances yet, add more pressing the + sign": [ + "" + ], + "Inventory products": [ + "" + ], + "Total price": [ + "" + ], + "Total tax": [ + "" + ], + "Order price": [ + "" + ], + "Net": [ + "" + ], + "Summary": [ + "" + ], + "Payments options": [ + "" + ], + "Auto refund deadline": [ + "" + ], + "Refund deadline": [ + "" + ], + "Pay deadline": [ + "" + ], + "Delivery date": [ + "" + ], + "Location": [ + "" + ], + "Max fee": [ + "" + ], + "Max wire fee": [ + "" + ], + "Wire fee amortization": [ + "" + ], + "Fullfilment url": [ + "" + ], + "Extra information": [ + "" + ], + "select a product first": [ + "" + ], + "should be greater than 0": [ + "" + ], + "cannot be greater than current stock and quantity previously added. max: %1$s": [ + "" + ], + "cannot be greater than current stock %1$s": [ + "" + ], + "Quantity": [ + "" + ], + "Order": [ + "" + ], + "claimed": [ + "" + ], + "copy url": [ + "" + ], + "pay at": [ + "" + ], + "created at": [ + "" + ], + "Timeline": [ + "" + ], + "Payment details": [ + "" + ], + "Order status": [ + "" + ], + "Product list": [ + "" + ], + "paid": [ + "" + ], + "wired": [ + "" + ], + "refunded": [ + "" + ], + "refund": [ + "" + ], + "Refunded amount": [ + "" + ], + "Deposit total": [ + "" + ], + "unpaid": [ + "" + ], + "Order status URL": [ + "" + ], + "Pay URI": [ + "" + ], + "Unknown order status. This is an error, please contact the administrator.": [ + "" + ], + "refund created successfully": [ + "" + ], + "could not create the refund": [ + "" + ], + "load newer orders": [ + "" + ], + "Date": [ + "" + ], + "Refund": [ + "" + ], + "load older orders": [ + "" + ], + "No orders has been found": [ + "" + ], + "date": [ + "" + ], + "amount": [ + "" + ], + "reason": [ + "" + ], + "Max refundable:": [ + "" + ], + "Reason": [ + "" + ], + "duplicated": [ + "" + ], + "requested by the customer": [ + "" + ], + "other": [ + "" + ], + "go to order id": [ + "" + ], + "Paid": [ + "" + ], + "Refunded": [ + "" + ], + "Not wired": [ + "" + ], + "All": [ + "" + ], + "could not create product": [ + "" + ], + "Sell": [ + "" + ], + "Profit": [ + "" + ], + "Sold": [ + "" + ], + "product updated successfully": [ + "" + ], + "could not update the product": [ + "" + ], + "product delete successfully": [ + "" + ], + "could not delete the product": [ + "" + ], + "Tips": [ + "" + ], + "Committed amount": [ + "" + ], + "Exchange initial amount": [ + "" + ], + "Merchant initial amount": [ + "" + ], + "There is no tips yet, add more pressing the + sign": [ + "" + ], + "cannot be empty": [ + "" + ], + "check the id, doest look valid": [ + "" + ], + "should have 52 characters, current %1$s": [ + "" + ], + "URL doesn't have the right format": [ + "" + ], + "Transfer ID": [ + "" + ], + "Account Address": [ + "" + ], + "Exchange URL": [ + "" + ], + "could not inform transfer": [ + "" + ], + "load newer transfers": [ + "" + ], + "Credit": [ + "" + ], + "Confirmed": [ + "" + ], + "Verified": [ + "" + ], + "Executed at": [ + "" + ], + "yes": [ + "" + ], + "no": [ + "" + ], + "unknown": [ + "" + ], + "load older transfers": [ + "" + ], + "There is no transfer yet, add more pressing the + sign": [ + "" + ] + } + } +}; + diff --git a/packages/backend/src/i18n/sv.po b/packages/backend/src/i18n/sv.po new file mode 100644 index 0000000..6b35bd0 --- /dev/null +++ b/packages/backend/src/i18n/sv.po @@ -0,0 +1,1057 @@ +# This file is part of TALER +# (C) 2016 GNUnet e.V. +# +# TALER is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# +# TALER is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# TALER; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "" + +#: src/InstanceRoutes.tsx:110 +#, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:289 +#, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "" + +#: src/components/form/InputDate.tsx:81 +#, c-format +msgid "clear" +msgstr "" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "" + +#: src/components/form/InputLocation.tsx:38 +#, c-format +msgid "Town location" +msgstr "" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:59 +#, c-format +msgid "Product id" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "" + +#: src/components/form/InputStock.tsx:105 +#, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, c-format +msgid "Orders" +msgstr "" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "" + +#: src/components/menu/SideBar.tsx:87 +#, c-format +msgid "Connection" +msgstr "" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "" + +#: src/components/menu/SideBar.tsx:116 +#, c-format +msgid "New" +msgstr "" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, c-format +msgid "Delete" +msgstr "" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, c-format +msgid "Net" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, c-format +msgid "Location" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, c-format +msgid "should be greater than 0" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, c-format +msgid "Order status" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, c-format +msgid "Product list" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, c-format +msgid "could not create the refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:108 +#, c-format +msgid "Refunded" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:109 +#, c-format +msgid "Not wired" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, c-format +msgid "Transfer ID" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, c-format +msgid "Account Address" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, c-format +msgid "could not inform transfer" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, c-format +msgid "load newer transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, c-format +msgid "Confirmed" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, c-format +msgid "Executed at" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, c-format +msgid "load older transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "" diff --git a/packages/backend/src/i18n/taler-merchant-backoffice.pot b/packages/backend/src/i18n/taler-merchant-backoffice.pot new file mode 100644 index 0000000..21fd863 --- /dev/null +++ b/packages/backend/src/i18n/taler-merchant-backoffice.pot @@ -0,0 +1,1054 @@ +# This file is part of GNU Taler +# (C) 2021 Taler Systems S.A. +# GNU Taler is free software; you can redistribute it and/or modify it under the +# terms of the GNU General Public License as published by the Free Software +# Foundation; either version 3, or (at your option) any later version. +# GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR +# A PARTICULAR PURPOSE. See the GNU General Public License for more details. +# You should have received a copy of the GNU General Public License along with +# GNU Taler; see the file COPYING. If not, see +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: Taler Wallet\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2016-11-23 00:00+0100\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: src/ApplicationReadyRoutes.tsx:50 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:299 +#, c-format +msgid "Access denied" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:51 src/InstanceRoutes.tsx:118 +#: src/InstanceRoutes.tsx:300 +#, c-format +msgid "Check your token is valid" +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:72 +#, c-format +msgid "Couldn't access the server." +msgstr "" + +#: src/ApplicationReadyRoutes.tsx:73 +#, c-format +msgid "Could not infer instance id from url %1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:109 +#, c-format +msgid "HTTP status #%1$s: Server reported a problem" +msgstr "" + +#: src/InstanceRoutes.tsx:110 +#, c-format +msgid "Got message: \"%1$s\" from: %2$s" +msgstr "" + +#: src/InstanceRoutes.tsx:127 +#, c-format +msgid "No default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:128 +#, c-format +msgid "" +"in order to use merchant backoffice, you should create the default instance" +msgstr "" + +#: src/InstanceRoutes.tsx:288 +#, c-format +msgid "Server reported a problem: HTTP status #%1$s" +msgstr "" + +#: src/InstanceRoutes.tsx:289 +#, c-format +msgid "Got message: %1$s from: %2$s" +msgstr "" + +#: src/components/exception/login.tsx:46 +#, c-format +msgid "Login required" +msgstr "" + +#: src/components/exception/login.tsx:49 +#, c-format +msgid "" +"Please enter your auth token. Token should have \"secret-token:\" and start " +"with Bearer or ApiKey" +msgstr "" + +#: src/components/exception/login.tsx:86 src/components/modal/index.tsx:53 +#: src/components/modal/index.tsx:75 src/paths/admin/create/CreatePage.tsx:115 +#: src/paths/instance/orders/create/CreatePage.tsx:325 +#: src/paths/instance/products/create/CreatePage.tsx:51 +#: src/paths/instance/products/list/Table.tsx:174 +#: src/paths/instance/products/list/Table.tsx:228 +#: src/paths/instance/products/update/UpdatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:134 +#, c-format +msgid "Confirm" +msgstr "" + +#: src/components/form/InputArray.tsx:72 +#, c-format +msgid "The value %1$s is invalid for a payment url" +msgstr "" + +#: src/components/form/InputDate.tsx:67 +#: src/paths/instance/orders/list/index.tsx:123 +#, c-format +msgid "pick a date" +msgstr "" + +#: src/components/form/InputDate.tsx:81 +#, c-format +msgid "clear" +msgstr "" + +#: src/components/form/InputDate.tsx:83 +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "never" +msgstr "" + +#: src/components/form/InputImage.tsx:80 +#, c-format +msgid "Image should be smaller than 1 MB" +msgstr "" + +#: src/components/form/InputLocation.tsx:28 +#, c-format +msgid "Country" +msgstr "" + +#: src/components/form/InputLocation.tsx:30 +#: src/paths/admin/create/CreatePage.tsx:99 +#: src/paths/instance/transfers/list/Table.tsx:124 +#: src/paths/instance/update/UpdatePage.tsx:118 +#, c-format +msgid "Address" +msgstr "" + +#: src/components/form/InputLocation.tsx:34 +#, c-format +msgid "Building number" +msgstr "" + +#: src/components/form/InputLocation.tsx:35 +#, c-format +msgid "Building name" +msgstr "" + +#: src/components/form/InputLocation.tsx:36 +#, c-format +msgid "Street" +msgstr "" + +#: src/components/form/InputLocation.tsx:37 +#, c-format +msgid "Post code" +msgstr "" + +#: src/components/form/InputLocation.tsx:38 +#, c-format +msgid "Town location" +msgstr "" + +#: src/components/form/InputLocation.tsx:39 +#, c-format +msgid "Town" +msgstr "" + +#: src/components/form/InputLocation.tsx:40 +#, c-format +msgid "District" +msgstr "" + +#: src/components/form/InputLocation.tsx:41 +#, c-format +msgid "Country subdivision" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:59 +#, c-format +msgid "Product id" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:60 +#: src/components/product/ProductForm.tsx:99 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:122 +#: src/paths/instance/orders/list/Table.tsx:227 +#: src/paths/instance/products/list/Table.tsx:86 +#, c-format +msgid "Description" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:73 +#: src/components/form/InputTaxes.tsx:81 +#: src/paths/admin/create/CreatePage.tsx:87 src/paths/admin/list/Table.tsx:110 +#: src/paths/instance/details/DetailPage.tsx:76 +#: src/paths/instance/update/UpdatePage.tsx:106 +#, c-format +msgid "Name" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:102 +#, c-format +msgid "loading..." +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:108 +#, c-format +msgid "no products found" +msgstr "" + +#: src/components/form/InputSearchProduct.tsx:116 +#, c-format +msgid "no results" +msgstr "" + +#: src/components/form/InputSecured.tsx:33 +#, c-format +msgid "Deleting" +msgstr "" + +#: src/components/form/InputSecured.tsx:34 +#, c-format +msgid "Changing" +msgstr "" + +#: src/components/form/InputSecured.tsx:60 +#, c-format +msgid "Manage token" +msgstr "" + +#: src/components/form/InputSecured.tsx:83 +#, c-format +msgid "Update" +msgstr "" + +#: src/components/form/InputSecured.tsx:100 +#: src/paths/instance/orders/create/CreatePage.tsx:252 +#: src/paths/instance/orders/create/CreatePage.tsx:273 +#, c-format +msgid "Remove" +msgstr "" + +#: src/components/form/InputSecured.tsx:106 src/components/modal/index.tsx:52 +#: src/components/modal/index.tsx:73 src/paths/admin/create/CreatePage.tsx:114 +#: src/paths/instance/orders/create/CreatePage.tsx:324 +#: src/paths/instance/products/create/CreatePage.tsx:50 +#: src/paths/instance/products/list/Table.tsx:166 +#: src/paths/instance/products/list/Table.tsx:218 +#: src/paths/instance/products/update/UpdatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:88 +#: src/paths/instance/update/UpdatePage.tsx:133 +#, c-format +msgid "Cancel" +msgstr "" + +#: src/components/form/InputStock.tsx:91 +#, c-format +msgid "Manage stock" +msgstr "" + +#: src/components/form/InputStock.tsx:93 +#, c-format +msgid "Infinite" +msgstr "" + +#: src/components/form/InputStock.tsx:105 +#, c-format +msgid "lost cannot be greater that current + incoming (max %1$s)" +msgstr "" + +#: src/components/form/InputStock.tsx:111 +#, c-format +msgid "current stock will change from %1$s to %2$s" +msgstr "" + +#: src/components/form/InputStock.tsx:112 +#, c-format +msgid "current stock will stay at %1$s" +msgstr "" + +#: src/components/form/InputStock.tsx:129 +#: src/paths/instance/products/list/Table.tsx:204 +#, c-format +msgid "Incoming" +msgstr "" + +#: src/components/form/InputStock.tsx:130 +#: src/paths/instance/products/list/Table.tsx:205 +#, c-format +msgid "Lost" +msgstr "" + +#: src/components/form/InputStock.tsx:142 +#, c-format +msgid "Current" +msgstr "" + +#: src/components/form/InputStock.tsx:145 +#, c-format +msgid "without stock" +msgstr "" + +#: src/components/form/InputStock.tsx:150 +#, c-format +msgid "Next restock" +msgstr "" + +#: src/components/form/InputStock.tsx:152 +#, c-format +msgid "Delivery address" +msgstr "" + +#: src/components/form/InputTaxes.tsx:73 +#, c-format +msgid "this product has no taxes" +msgstr "" + +#: src/components/form/InputTaxes.tsx:77 +#: src/paths/instance/orders/details/DetailPage.tsx:145 +#: src/paths/instance/orders/details/DetailPage.tsx:296 +#: src/paths/instance/orders/list/Table.tsx:116 +#: src/paths/instance/transfers/create/CreatePage.tsx:84 +#, c-format +msgid "Amount" +msgstr "" + +#: src/components/form/InputTaxes.tsx:78 +#, c-format +msgid "currency and value separated with colon" +msgstr "" + +#: src/components/form/InputTaxes.tsx:84 +#: src/paths/instance/orders/create/InventoryProductForm.tsx:78 +#, c-format +msgid "Add" +msgstr "" + +#: src/components/menu/SideBar.tsx:53 +#, c-format +msgid "Instance" +msgstr "" + +#: src/components/menu/SideBar.tsx:59 +#, c-format +msgid "Settings" +msgstr "" + +#: src/components/menu/SideBar.tsx:65 +#: src/paths/instance/orders/list/Table.tsx:60 +#, c-format +msgid "Orders" +msgstr "" + +#: src/components/menu/SideBar.tsx:71 +#: src/paths/instance/orders/create/CreatePage.tsx:258 +#: src/paths/instance/products/list/Table.tsx:48 +#, c-format +msgid "Products" +msgstr "" + +#: src/components/menu/SideBar.tsx:77 +#: src/paths/instance/transfers/list/Table.tsx:65 +#, c-format +msgid "Transfers" +msgstr "" + +#: src/components/menu/SideBar.tsx:87 +#, c-format +msgid "Connection" +msgstr "" + +#: src/components/menu/SideBar.tsx:112 src/paths/admin/list/Table.tsx:57 +#, c-format +msgid "Instances" +msgstr "" + +#: src/components/menu/SideBar.tsx:116 +#, c-format +msgid "New" +msgstr "" + +#: src/components/menu/SideBar.tsx:122 +#, c-format +msgid "List" +msgstr "" + +#: src/components/menu/SideBar.tsx:129 +#, c-format +msgid "Log out" +msgstr "" + +#: src/components/modal/index.tsx:74 +#, c-format +msgid "Clear" +msgstr "" + +#: src/components/modal/index.tsx:110 src/components/modal/index.tsx:111 +#, c-format +msgid "should be the same" +msgstr "" + +#: src/components/modal/index.tsx:111 +#, c-format +msgid "cannot be the same as before" +msgstr "" + +#: src/components/modal/index.tsx:114 +#, c-format +msgid "" +"You are updating the authorization token from instance %1$s with id %2$s" +msgstr "" + +#: src/components/modal/index.tsx:124 +#, c-format +msgid "Old token" +msgstr "" + +#: src/components/modal/index.tsx:125 +#, c-format +msgid "New token" +msgstr "" + +#: src/components/modal/index.tsx:127 +#, c-format +msgid "Clearing the auth token will mean public access to the instance" +msgstr "" + +#: src/components/product/ProductForm.tsx:96 +#: src/paths/admin/create/CreatePage.tsx:85 src/paths/admin/list/Table.tsx:109 +#: src/paths/instance/transfers/list/Table.tsx:122 +#, c-format +msgid "ID" +msgstr "" + +#: src/components/product/ProductForm.tsx:98 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:121 +#: src/paths/instance/products/list/Table.tsx:85 +#, c-format +msgid "Image" +msgstr "" + +#: src/components/product/ProductForm.tsx:100 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:123 +#, c-format +msgid "Unit" +msgstr "" + +#: src/components/product/ProductForm.tsx:101 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:124 +#: src/paths/instance/products/list/Table.tsx:162 +#: src/paths/instance/products/list/Table.tsx:214 +#, c-format +msgid "Price" +msgstr "" + +#: src/components/product/ProductForm.tsx:103 +#: src/paths/instance/products/list/Table.tsx:90 +#, c-format +msgid "Stock" +msgstr "" + +#: src/components/product/ProductForm.tsx:105 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:128 +#: src/paths/instance/products/list/Table.tsx:88 +#, c-format +msgid "Taxes" +msgstr "" + +#: src/index.tsx:75 +#, c-format +msgid "Server not found" +msgstr "" + +#: src/index.tsx:85 +#, c-format +msgid "Couldn't access the server" +msgstr "" + +#: src/index.tsx:87 src/index.tsx:99 +#, c-format +msgid "Got message %1$s from %2$s" +msgstr "" + +#: src/index.tsx:97 +#, c-format +msgid "Unexpected Error" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:89 +#: src/paths/instance/update/UpdatePage.tsx:108 +#, c-format +msgid "Auth token" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:91 +#: src/paths/instance/details/DetailPage.tsx:77 +#: src/paths/instance/update/UpdatePage.tsx:110 +#, c-format +msgid "Account address" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:93 +#: src/paths/instance/update/UpdatePage.tsx:112 +#, c-format +msgid "Default max deposit fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:95 +#: src/paths/instance/update/UpdatePage.tsx:114 +#, c-format +msgid "Default max wire fee" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:97 +#: src/paths/instance/update/UpdatePage.tsx:116 +#, c-format +msgid "Default wire fee amortization" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:103 +#: src/paths/instance/update/UpdatePage.tsx:122 +#, c-format +msgid "Jurisdiction" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:107 +#: src/paths/instance/update/UpdatePage.tsx:126 +#, c-format +msgid "Default pay delay" +msgstr "" + +#: src/paths/admin/create/CreatePage.tsx:109 +#: src/paths/instance/update/UpdatePage.tsx:128 +#, c-format +msgid "Default wire transfer delay" +msgstr "" + +#: src/paths/admin/create/index.tsx:58 +#, c-format +msgid "could not create instance" +msgstr "" + +#: src/paths/admin/list/Table.tsx:63 src/paths/admin/list/Table.tsx:131 +#: src/paths/instance/transfers/list/Table.tsx:71 +#, c-format +msgid "Delete" +msgstr "" + +#: src/paths/admin/list/Table.tsx:128 +#, c-format +msgid "Edit" +msgstr "" + +#: src/paths/admin/list/Table.tsx:149 +#: src/paths/instance/products/list/Table.tsx:245 +#, c-format +msgid "There is no instances yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:237 +#, c-format +msgid "Inventory products" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:286 +#, c-format +msgid "Total price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:287 +#, c-format +msgid "Total tax" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:289 +#: src/paths/instance/orders/create/CreatePage.tsx:297 +#, c-format +msgid "Order price" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:295 +#, c-format +msgid "Net" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:300 +#: src/paths/instance/orders/details/DetailPage.tsx:144 +#: src/paths/instance/orders/details/DetailPage.tsx:295 +#: src/paths/instance/orders/list/Table.tsx:117 +#, c-format +msgid "Summary" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:302 +#, c-format +msgid "Payments options" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:303 +#, c-format +msgid "Auto refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:304 +#, c-format +msgid "Refund deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:305 +#, c-format +msgid "Pay deadline" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:307 +#, c-format +msgid "Delivery date" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:308 +#, c-format +msgid "Location" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:312 +#, c-format +msgid "Max fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:313 +#, c-format +msgid "Max wire fee" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:314 +#, c-format +msgid "Wire fee amortization" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:315 +#, c-format +msgid "Fullfilment url" +msgstr "" + +#: src/paths/instance/orders/create/CreatePage.tsx:318 +#, c-format +msgid "Extra information" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:44 +#, c-format +msgid "select a product first" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:51 +#, c-format +msgid "should be greater than 0" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:58 +#, c-format +msgid "" +"cannot be greater than current stock and quantity previously added. max: %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:64 +#, c-format +msgid "cannot be greater than current stock %1$s" +msgstr "" + +#: src/paths/instance/orders/create/InventoryProductForm.tsx:76 +#: src/paths/instance/orders/create/NonInventoryProductForm.tsx:126 +#, c-format +msgid "Quantity" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:92 +#: src/paths/instance/orders/details/DetailPage.tsx:235 +#: src/paths/instance/orders/details/DetailPage.tsx:333 +#, c-format +msgid "Order" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:93 +#, c-format +msgid "claimed" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:110 +#: src/paths/instance/orders/details/DetailPage.tsx:261 +#: src/paths/instance/orders/list/Table.tsx:136 +#, c-format +msgid "copy url" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:126 +#: src/paths/instance/orders/details/DetailPage.tsx:349 +#, c-format +msgid "pay at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:127 +#: src/paths/instance/orders/details/DetailPage.tsx:350 +#, c-format +msgid "created at" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:138 +#: src/paths/instance/orders/details/DetailPage.tsx:289 +#, c-format +msgid "Timeline" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:142 +#: src/paths/instance/orders/details/DetailPage.tsx:293 +#, c-format +msgid "Payment details" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:146 +#: src/paths/instance/orders/details/DetailPage.tsx:299 +#: src/paths/instance/orders/details/DetailPage.tsx:363 +#, c-format +msgid "Order status" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:156 +#: src/paths/instance/orders/details/DetailPage.tsx:308 +#, c-format +msgid "Product list" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:236 +#, c-format +msgid "paid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:238 +#, c-format +msgid "wired" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:241 +#, c-format +msgid "refunded" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:258 +#, c-format +msgid "refund" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:297 +#, c-format +msgid "Refunded amount" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:298 +#, c-format +msgid "Deposit total" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:336 +#, c-format +msgid "unpaid" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:364 +#, c-format +msgid "Order status URL" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:365 +#, c-format +msgid "Pay URI" +msgstr "" + +#: src/paths/instance/orders/details/DetailPage.tsx:383 +#, c-format +msgid "" +"Unknown order status. This is an error, please contact the administrator." +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:56 +#: src/paths/instance/orders/list/index.tsx:147 +#, c-format +msgid "refund created successfully" +msgstr "" + +#: src/paths/instance/orders/details/index.tsx:59 +#: src/paths/instance/orders/list/index.tsx:150 +#, c-format +msgid "could not create the refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:111 +#, c-format +msgid "load newer orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:115 +#, c-format +msgid "Date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:131 +#: src/paths/instance/orders/list/Table.tsx:223 +#, c-format +msgid "Refund" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:145 +#, c-format +msgid "load older orders" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:154 +#, c-format +msgid "No orders has been found" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:202 +#, c-format +msgid "date" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:203 +#, c-format +msgid "amount" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:204 +#, c-format +msgid "reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:224 +#, c-format +msgid "Max refundable:" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "Reason" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "duplicated" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "requested by the customer" +msgstr "" + +#: src/paths/instance/orders/list/Table.tsx:226 +#, c-format +msgid "other" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:91 +#, c-format +msgid "go to order id" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:107 +#, c-format +msgid "Paid" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:108 +#, c-format +msgid "Refunded" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:109 +#, c-format +msgid "Not wired" +msgstr "" + +#: src/paths/instance/orders/list/index.tsx:110 +#, c-format +msgid "All" +msgstr "" + +#: src/paths/instance/products/create/index.tsx:48 +#: src/paths/instance/products/update/index.tsx:64 +#, c-format +msgid "could not create product" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:87 +#, c-format +msgid "Sell" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:89 +#, c-format +msgid "Profit" +msgstr "" + +#: src/paths/instance/products/list/Table.tsx:91 +#, c-format +msgid "Sold" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:59 +#, c-format +msgid "product updated successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:62 +#, c-format +msgid "could not update the product" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:70 +#, c-format +msgid "product delete successfully" +msgstr "" + +#: src/paths/instance/products/list/index.tsx:73 +#, c-format +msgid "could not delete the product" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:59 +#, c-format +msgid "Tips" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:111 +#, c-format +msgid "Committed amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:112 +#, c-format +msgid "Exchange initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:113 +#, c-format +msgid "Merchant initial amount" +msgstr "" + +#: src/paths/instance/tips/list/Table.tsx:148 +#, c-format +msgid "There is no tips yet, add more pressing the + sign" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:50 +#: src/paths/instance/transfers/create/CreatePage.tsx:54 +#: src/paths/instance/transfers/create/CreatePage.tsx:55 +#: src/paths/instance/transfers/create/CreatePage.tsx:56 +#, c-format +msgid "cannot be empty" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:51 +#, c-format +msgid "check the id, doest look valid" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:52 +#, c-format +msgid "should have 52 characters, current %1$s" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:57 +#, c-format +msgid "URL doesn't have the right format" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:74 +#, c-format +msgid "Transfer ID" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:76 +#, c-format +msgid "Account Address" +msgstr "" + +#: src/paths/instance/transfers/create/CreatePage.tsx:82 +#: src/paths/instance/transfers/list/Table.tsx:125 +#, c-format +msgid "Exchange URL" +msgstr "" + +#: src/paths/instance/transfers/create/index.tsx:49 +#, c-format +msgid "could not inform transfer" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:118 +#, c-format +msgid "load newer transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:123 +#, c-format +msgid "Credit" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:126 +#, c-format +msgid "Confirmed" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:127 +#: src/paths/instance/transfers/list/index.tsx:60 +#, c-format +msgid "Verified" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:128 +#, c-format +msgid "Executed at" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "yes" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:138 +#: src/paths/instance/transfers/list/Table.tsx:139 +#, c-format +msgid "no" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:140 +#, c-format +msgid "unknown" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:145 +#, c-format +msgid "load older transfers" +msgstr "" + +#: src/paths/instance/transfers/list/Table.tsx:154 +#, c-format +msgid "There is no transfer yet, add more pressing the + sign" +msgstr "" diff --git a/packages/backend/src/index.tsx b/packages/backend/src/index.tsx new file mode 100644 index 0000000..0babb26 --- /dev/null +++ b/packages/backend/src/index.tsx @@ -0,0 +1,67 @@ +/* + This file is part of GNU Taler + (C) 2021 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see + */ + +/** +* +* @author Sebastian Javier Marchano (sebasjm) +*/ + +import { h, VNode, Fragment } from 'preact'; +import { BackendContextProvider } from './context/backend'; +import { TranslationProvider } from './context/translation'; +// import { Page as RequestPayment } from './RequestPayment'; +import "./css/pure-min.css" +import { Route, Router } from 'preact-router'; +// import OfferTip from './pages/OfferTip'; +// import {OfferRefund} from './pages/OfferRefund'; +// import DepletedTip from './pages/DepletedTip'; +// import RequestPayment from './pages/RequestPayment'; +// import ShowOrderDetails from './pages/ShowOrderDetails'; + +export default function Application(): VNode { + return ( + // + + + + + + // + ); +} + +function Footer() { + return
+

You can learn more about GNU Taler on our website.
+ Copyright © 2014—2021 Taler Systems SA

+
+} + +function ApplicationStatusRoutes(): VNode { + return + + {/* + + + + */} +
+ hello! +
} /> +
+