Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Svelte example project #3287

Merged
merged 3 commits into from
Aug 18, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion examples/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ electron | [done](./electron)
Framework | Status
---------------- | ------------------
plain javascript | [done](./vanilla)
angular | [done](./angular)
angular | [done](./angular)
react | [done](./react)
svelte | [done](./svelte)
vuejs | [done](./vue)
4 changes: 4 additions & 0 deletions examples/svelte/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
/node_modules/
/public/build/

.DS_Store
9 changes: 9 additions & 0 deletions examples/svelte/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
# RxDB in Svelte Demo

![](./screenshot.jpg)

This is a quick note-taking app that demonstrates how to use RxDB within a Svelte app.

```sh
npm i && npm run dev
```
30 changes: 30 additions & 0 deletions examples/svelte/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
{
"name": "svelte-app",
"version": "1.0.0",
"private": true,
"scripts": {
"build": "rollup -c",
"dev": "rollup -c -w",
"start": "sirv public --no-clear",
"test": "testcafe chrome -e test/ --hostname localhost --selector-timeout 8000"
},
"devDependencies": {
"@rollup/plugin-commonjs": "^17.0.0",
"@rollup/plugin-node-resolve": "^11.0.0",
"async-test-util": "^1.7.3",
"pouchdb-adapter-idb": "^7.2.2",
"rollup": "^2.3.4",
"rollup-plugin-css-only": "^3.1.0",
"rollup-plugin-livereload": "^2.0.0",
"rollup-plugin-node-builtins": "^2.1.2",
"rollup-plugin-svelte": "^7.0.0",
"rollup-plugin-terser": "^7.0.0",
"rxdb": "^9.21.0",
"rxjs": "^7.2.0",
"svelte": "^3.0.0",
"testcafe": "^1.15.2"
},
"dependencies": {
"sirv-cli": "^1.0.0"
}
}
Binary file added examples/svelte/public/favicon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
13 changes: 13 additions & 0 deletions examples/svelte/public/global.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
html, body {
position: relative;
width: 100%;
height: 100%;
}

body {
background-color: #f0f0f0;
color: #333;
margin: 50px 0 0 0;
box-sizing: border-box;
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen-Sans, Ubuntu, Cantarell, "Helvetica Neue", sans-serif;
}
19 changes: 19 additions & 0 deletions examples/svelte/public/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset='utf-8'>
<meta name='viewport' content='width=device-width,initial-scale=1'>

<title>Svelte app</title>

<link rel='icon' type='image/png' href='/favicon.png'>
<link rel='stylesheet' href='/global.css'>
<link rel='stylesheet' href='/build/bundle.css'>

<script>var global = globalThis</script>
<script defer src='/build/bundle.js'></script>
</head>

<body>
</body>
</html>
78 changes: 78 additions & 0 deletions examples/svelte/rollup.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
import svelte from 'rollup-plugin-svelte';
import commonjs from '@rollup/plugin-commonjs';
import resolve from '@rollup/plugin-node-resolve';
import livereload from 'rollup-plugin-livereload';
import { terser } from 'rollup-plugin-terser';
import css from 'rollup-plugin-css-only';
import builtins from 'rollup-plugin-node-builtins';

const production = !process.env.ROLLUP_WATCH;

function serve() {
let server;

function toExit() {
if (server) server.kill(0);
}

return {
writeBundle() {
if (server) return;
server = require('child_process').spawn('npm', ['run', 'start', '--', '--dev'], {
stdio: ['ignore', 'inherit', 'inherit'],
shell: true
});

process.on('SIGTERM', toExit);
process.on('exit', toExit);
}
};
}

export default {
input: 'src/main.js',
output: {
sourcemap: true,
format: 'iife',
name: 'app',
file: 'public/build/bundle.js'
},
plugins: [
svelte({
compilerOptions: {
// enable run-time checks when not in production
dev: !production
}
}),
builtins(),
// we'll extract any component CSS out into
// a separate file - better for performance
css({ output: 'bundle.css' }),

// If you have external dependencies installed from
// npm, you'll most likely need these plugins. In
// some cases you'll need additional configuration -
// consult the documentation for details:
// https://github.com/rollup/plugins/tree/master/packages/commonjs
resolve({
browser: true,
dedupe: ['svelte']
}),
commonjs(),

// In dev mode, call `npm run start` once
// the bundle has been generated
!production && serve(),

// Watch the `public` directory and refresh the
// browser on changes when not in production
!production && livereload('public'),

// If we're building for production (npm run build
// instead of npm run dev), minify
production && terser()
],
watch: {
clearScreen: false
}
};
Binary file added examples/svelte/screenshot.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
121 changes: 121 additions & 0 deletions examples/svelte/scripts/setupTypeScript.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
// @ts-check

/** This script modifies the project to support TS code in .svelte files like:

<script lang="ts">
export let name: string;
</script>

As well as validating the code for CI.
*/

/** To work on this script:
rm -rf test-template template && git clone sveltejs/template test-template && node scripts/setupTypeScript.js test-template
*/

const fs = require("fs")
const path = require("path")
const { argv } = require("process")

const projectRoot = argv[2] || path.join(__dirname, "..")

// Add deps to pkg.json
const packageJSON = JSON.parse(fs.readFileSync(path.join(projectRoot, "package.json"), "utf8"))
packageJSON.devDependencies = Object.assign(packageJSON.devDependencies, {
"svelte-check": "^2.0.0",
"svelte-preprocess": "^4.0.0",
"@rollup/plugin-typescript": "^8.0.0",
"typescript": "^4.0.0",
"tslib": "^2.0.0",
"@tsconfig/svelte": "^2.0.0"
})

// Add script for checking
packageJSON.scripts = Object.assign(packageJSON.scripts, {
"check": "svelte-check --tsconfig ./tsconfig.json"
})

// Write the package JSON
fs.writeFileSync(path.join(projectRoot, "package.json"), JSON.stringify(packageJSON, null, " "))

// mv src/main.js to main.ts - note, we need to edit rollup.config.js for this too
const beforeMainJSPath = path.join(projectRoot, "src", "main.js")
const afterMainTSPath = path.join(projectRoot, "src", "main.ts")
fs.renameSync(beforeMainJSPath, afterMainTSPath)

// Switch the app.svelte file to use TS
const appSveltePath = path.join(projectRoot, "src", "App.svelte")
let appFile = fs.readFileSync(appSveltePath, "utf8")
appFile = appFile.replace("<script>", '<script lang="ts">')
appFile = appFile.replace("export let name;", 'export let name: string;')
fs.writeFileSync(appSveltePath, appFile)

// Edit rollup config
const rollupConfigPath = path.join(projectRoot, "rollup.config.js")
let rollupConfig = fs.readFileSync(rollupConfigPath, "utf8")

// Edit imports
rollupConfig = rollupConfig.replace(`'rollup-plugin-terser';`, `'rollup-plugin-terser';
import sveltePreprocess from 'svelte-preprocess';
import typescript from '@rollup/plugin-typescript';`)

// Replace name of entry point
rollupConfig = rollupConfig.replace(`'src/main.js'`, `'src/main.ts'`)

// Add preprocessor
rollupConfig = rollupConfig.replace(
'compilerOptions:',
'preprocess: sveltePreprocess({ sourceMap: !production }),\n\t\t\tcompilerOptions:'
);

// Add TypeScript
rollupConfig = rollupConfig.replace(
'commonjs(),',
'commonjs(),\n\t\ttypescript({\n\t\t\tsourceMap: !production,\n\t\t\tinlineSources: !production\n\t\t}),'
);
fs.writeFileSync(rollupConfigPath, rollupConfig)

// Add TSConfig
const tsconfig = `{
"extends": "@tsconfig/svelte/tsconfig.json",

"include": ["src/**/*"],
"exclude": ["node_modules/*", "__sapper__/*", "public/*"]
}`
const tsconfigPath = path.join(projectRoot, "tsconfig.json")
fs.writeFileSync(tsconfigPath, tsconfig)

// Add global.d.ts
const dtsPath = path.join(projectRoot, "src", "global.d.ts")
fs.writeFileSync(dtsPath, `/// <reference types="svelte" />`)

// Delete this script, but not during testing
if (!argv[2]) {
// Remove the script
fs.unlinkSync(path.join(__filename))

// Check for Mac's DS_store file, and if it's the only one left remove it
const remainingFiles = fs.readdirSync(path.join(__dirname))
if (remainingFiles.length === 1 && remainingFiles[0] === '.DS_store') {
fs.unlinkSync(path.join(__dirname, '.DS_store'))
}

// Check if the scripts folder is empty
if (fs.readdirSync(path.join(__dirname)).length === 0) {
// Remove the scripts folder
fs.rmdirSync(path.join(__dirname))
}
}

// Adds the extension recommendation
fs.mkdirSync(path.join(projectRoot, ".vscode"), { recursive: true })
fs.writeFileSync(path.join(projectRoot, ".vscode", "extensions.json"), `{
"recommendations": ["svelte.svelte-vscode"]
}
`)

console.log("Converted to TypeScript.")

if (fs.existsSync(path.join(projectRoot, "node_modules"))) {
console.log("\nYou will need to re-run your dependency manager to get started.")
}
29 changes: 29 additions & 0 deletions examples/svelte/src/App.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
<script>
import NoteEditor from './NoteEditor.svelte';
import NoteList from './NoteList.svelte';
</script>

<main>
<h1>RxDB Svelte Note App Demo</h1>
<div>
<NoteList />
<NoteEditor />
</div>
</main>

<style>
main {
margin: auto;
max-width: 1080px;
padding: 10px;
border-radius: 6px;
background-color: #fff;
}
h1 {
text-align: center;
}
div {
display: flex;
flex-direction: column;
}
</style>
68 changes: 68 additions & 0 deletions examples/svelte/src/NoteEditor.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
<script>
import { db, selectedNote, name, body } from './store';

const isEmptyObject = (obj) => obj && Object.keys(obj).length === 0 && obj.constructor === Object;

const resetForm = () => {
name.set('');
body.set('');
selectedNote.set({});
};

const saveNote = async () => {
const db$ = await db();
if (isEmptyObject($selectedNote)) {
await db$.notes
.insert({
name: $name,
body: $body,
createdAt: new Date().getTime(),
updatedAt: new Date().getTime(),
})
.then(resetForm);
} else {
await $selectedNote
.update({
$set: {
name: $name,
body: $body,
updatedAt: new Date().getTime(),
},
})
.then(resetForm);
}
};
</script>

<div>
<h2>NoteEditor.svelte</h2>
<input bind:value={$name} placeholder="Note Title" />
<textarea bind:value={$body} placeholder="Note Content..." />
<button on:click={saveNote}>Save Note</button>
</div>

<style>
h2 {
margin-top: 0;
}
div {
margin: 10px 20px 20px 20px;
padding: 20px;
box-sizing: border-box;
background: #fffff3;
border-radius: 3px;
border: 1px solid #f7e493;
}

input,
textarea {
margin: auto;
display: block;
width: 100%;
margin-bottom: 10px;
resize: vertical;
}
textarea {
min-height: 200px;
}
</style>
Loading