Skip to content

Commit

Permalink
Merge pull request #477 from saul-jb/feat/vue-template
Browse files Browse the repository at this point in the history
Add Vue Template
  • Loading branch information
lucksus authored Dec 17, 2024
2 parents 3b5397a + 0d8b523 commit 20eef54
Show file tree
Hide file tree
Showing 14 changed files with 370 additions and 1 deletion.
5 changes: 4 additions & 1 deletion packages/create/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,10 @@ async function run() {
type: "multiselect",
name: "template",
message: "Pick a template",
choices: [{ title: "preact", value: "preact", selected: true }],
choices: [
{ title: "preact", value: "preact", selected: true }
{ title: "vue", value: "vue" }
],
hint: "- Space to select. Return to submit",
},
]);
Expand Down
17 changes: 17 additions & 0 deletions packages/create/templates/vue/README
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Create Flux Plugin

Bootstrap a new [Flux](https://fluxsocial.io) plugin for your community.

[Documentation](https://docs.fluxsocial.io/create-flux-plugin/getting-started/introduction.html)

Install deps and start building:

```bash [npm]
cd [plugin-name]
npm install
npm run dev
```

## Prerequisites

Flux runs on top of [AD4M](https://ad4m.dev), a p2p framework where all data is stored and shared. In order to build a new Flux app you need to [download](https://ad4m.dev/download) and install AD4M.
20 changes: 20 additions & 0 deletions packages/create/templates/vue/gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
node_modules
dist
package-lock.json

# Log files
*.log

# Editor directories and files
.idea
.vscode
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw?
*.turbo
dev-dist
vite.config.ts.timestamp*

cachedb
1 change: 1 addition & 0 deletions packages/create/templates/vue/globals.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
declare module "*.module.css";
41 changes: 41 additions & 0 deletions packages/create/templates/vue/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
<!doctype html>
<html class="dark" lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Flux App</title>
<style>
html {
box-sizing: border-box;
}
body {
margin: 0;
font-family: Arial, Helvetica, sans-serif;
color: var(--j-color-ui-800);
background: var(--j-color-white);
}
*,
*:before,
*:after {
box-sizing: inherit;
}
flux-app {
height: 100%;
display: block;
}
</style>
</head>
<body>
<flux-container>
<flux-plugin></flux-plugin>
</flux-container>

<script type="module">
import Plugin from "./src/main.ts";
import "@coasys/flux-container";

customElements.define("flux-plugin", Plugin);
</script>
</body>
</html>
48 changes: 48 additions & 0 deletions packages/create/templates/vue/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
{
"name": "my-first-vue-flux-plugin",
"version": "0.0.1",
"fluxplugin": {
"name": "Todos",
"description": "Work on a collaborative todo list",
"icon": "list-check"
},
"keywords": [
"flux-plugin",
"ad4m-view"
],
"type": "module",
"files": [
"dist"
],
"main": "./dist/main.umd.cjs",
"module": "./dist/main.js",
"exports": {
".": {
"import": "./dist/main.js",
"require": "./dist/main.umd.cjs"
}
},
"scripts": {
"start": "vite",
"dev": "vite",
"build": "vite build",
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"description": "",
"dependencies": {
"@coasys/ad4m": "0.10.0-rc7.local-ai.4",
"@coasys/ad4m-vue-hooks": "^0.10.0-rc7.local-ai.4",
"@coasys/flux-api": "0.10.0-rc7.local-ai.4",
"vue": "^3.5.12"
},
"devDependencies": {
"@babel/plugin-proposal-class-properties": "^7.18.6",
"@babel/plugin-proposal-decorators": "^7.21.0",
"@coasys/flux-container": "0.10.0-rc7.local-ai.4",
"@vitejs/plugin-vue": "^5.1.4",
"vite": "^5.4.10",
"vite-plugin-css-injected-by-js": "^3.5.2"
}
}
28 changes: 28 additions & 0 deletions packages/create/templates/vue/src/Plugin.module.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
.appContainer {
margin: 0 auto;
padding: var(--j-space-800);
width: 100%;
max-width: 800px;
}

.titleInput {
width: 100%;
font-size: var(--j-font-size-700);
height: var(--j-size-xl);
padding: 0;
color: var(--j-color-black);
background: transparent;
border: 0;
}

.titleInput::placeholder {
color: var(--j-color-ui-400);
}

.titleInput:focus {
outline: 0;
}

.doneTodo {
text-decoration: line-through;
}
29 changes: 29 additions & 0 deletions packages/create/templates/vue/src/Plugin.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
<template>
<div v-if="hasPerspective" :class="styles.appContainer">
<TodoView :perspective="perspective" :source="source" />
</div>

<template v-else>
No perspective or agent client
</template>
</template>

<script setup lang="ts">
import styles from "./Plugin.module.css";
import type { PerspectiveProxy } from "@coasys/ad4m";
import type { AgentClient } from "@coasys/ad4m";
import { computed } from 'vue';
import TodoView from "./components/TodoView.vue";
type Props = Partial<{
agent: AgentClient;
perspective: PerspectiveProxy;
source: string;
}>
const { perspective, agent, source } = defineProps<Props>();
const hasPerspective = computed(
() => perspective?.uuid != null && agent != null
)
</script>
95 changes: 95 additions & 0 deletions packages/create/templates/vue/src/components/TodoView.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
<template>
<div>
<j-box pt="900" pb="400">
<j-text
uppercase
size="300"
weight="800"
color="primary-500"
variant="success"
>
Make a new todo
</j-text>
</j-box>

<input
autoFocus
:class="styles.titleInput"
placeholder="Write a title"
v-model="title"
@keydown.enter="createTodo"
></input>

<j-box pt="500">
<j-flex gap="300" direction="column">
<j-box v-for="todo in todos" bg="ui-50" p="400" radius="md">
<j-flex j="between">
<div :class="{ [styles.doneTodo]: todo.done }">
<j-checkbox
@change="toggleTodo({ id: todo.id, done: $event.target.checked })"
:checked="todo.done"
style="--j-border-radius: 50%;"
size="sm"
>
<j-icon slot="checkmark" size="xs" name="check"></j-icon>
<j-text size="500" nomargin>
{{ todo.title }}
</j-text>
<j-text size="500" nomargin>
{{ todo.desc }}
</j-text>
</j-checkbox>
</div>
<j-button @click="deleteTodo(todo.id)">Delete</j-button>
</j-flex>
</j-box>
</j-flex>
</j-box>
</div>
</template>

<script setup lang="ts">
import { PerspectiveProxy } from "@coasys/ad4m";
import { useSubjects } from "@coasys/ad4m-vue-hooks";
import { ref, computed, onMounted } from 'vue';
import Todo from "../subjects/Todo";
import styles from "../Plugin.module.css";
type Props = {
perspective: PerspectiveProxy;
source: string;
};
const { perspective, source } = defineProps<Props>();
const title = ref("")
onMounted(async () => {
await perspective.ensureSDNASubjectClass(Todo);
});
const { entries: todos, repo } = useSubjects({
perspective: computed(() => perspective),
source: computed(() => source),
subject: Todo,
});
const createTodo = () => {
repo.value
.create({ title: title.value })
.then(() => {
title.value = "";
})
.catch(console.log);
}
const toggleTodo = ({ id, done }) => {
repo.value.update(id, { done }).catch(console.log);
}
const deleteTodo = (id: string) => {
repo.value.remove(id).catch(console.log);
}
</script>
6 changes: 6 additions & 0 deletions packages/create/templates/vue/src/main.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { defineCustomElement } from 'vue';
import Plugin from "./Plugin.vue";

const element = defineCustomElement(Plugin, { shadowRoot: false });

export default element;
6 changes: 6 additions & 0 deletions packages/create/templates/vue/src/shims-vue.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
/* eslint-disable */
declare module '*.vue' {
import type { DefineComponent } from 'vue'
const component: DefineComponent<{}, {}, any>
export default component
}
33 changes: 33 additions & 0 deletions packages/create/templates/vue/src/subjects/Todo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { SDNAClass, SubjectProperty, SubjectFlag } from "@coasys/ad4m";

@SDNAClass({
name: "Todo",
})
export default class Todo {
@SubjectFlag({
through: "flux://entry_type",
value: "flux://has_todo",
})
type: string;

@SubjectProperty({
through: "rdf://title",
writable: true,
resolveLanguage: "literal",
})
title: string;

@SubjectProperty({
through: "rdf://description",
writable: true,
resolveLanguage: "literal",
})
desc: string;

@SubjectProperty({
through: "rdf://status",
writable: true,
resolveLanguage: "literal",
})
done: boolean;
}
9 changes: 9 additions & 0 deletions packages/create/templates/vue/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"compilerOptions": {
"downlevelIteration": true,
"experimentalDecorators": true,
"skipLibCheck": true,
"baseUrl": "/"
},
"include": ["./globals.d.ts", "src/**/*.ts"]
}
33 changes: 33 additions & 0 deletions packages/create/templates/vue/vite.config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { defineConfig } from "vite";
import { resolve } from "path";
import vue from '@vitejs/plugin-vue'
import cssInjectedByJsPlugin from "vite-plugin-css-injected-by-js";

export default defineConfig({
plugins: [
vue({
template: {
compilerOptions: {
isCustomElement: tag => tag.startsWith('j-')
}
}
}),
cssInjectedByJsPlugin(),
],
optimizeDeps: {
esbuildOptions: {
tsconfigRaw: {
compilerOptions: {
experimentalDecorators: true,
},
},
},
},
build: {
lib: {
entry: resolve(__dirname, "./src/main.ts"),
name: "Main",
fileName: "main",
},
},
});

0 comments on commit 20eef54

Please sign in to comment.