# neo-push
Example blog site built with Neo4j GraphQL & React.js. This application showcases features of Neo4j GraphQL such as;
1. Nested Mutations
2. @auth directive
3. OGM(Object Graph Mapper)
There are only two custom resolvers in the server; sign up plus sign in. The lack of custom logic is showcasing how quickly developers can build, both powerful and secure, applications ontop of Neo4j. Its worth nothing this entire application contains zero 'raw' cypher. All interaction's with the database are done through the generated GraphQL Schema via either the OGM or Apollo Server.
![overview](assets/overview.gif)
![arrows of data](assets/arrows.png)
**Diagram from https://arrows.app/**
```graphql
type User {
id: ID! @id
email: String!
password: String!
createdBlogs: [Blog] @relationship(type: "HAS_BLOG", direction: OUT)
authorsBlogs: [Blog] @relationship(type: "CAN_POST", direction: OUT)
password: String! @private
createdAt: DateTime @timestamp(operations: [CREATE])
updatedAt: DateTime @timestamp(operations: [UPDATE])
}
type Blog {
id: ID! @id
name: String!
creator: User @relationship(type: "HAS_BLOG", direction: IN)
authors: [User] @relationship(type: "CAN_POST", direction: IN)
posts: [Post] @relationship(type: "HAS_POST", direction: OUT)
createdAt: DateTime @timestamp(operations: [CREATE])
updatedAt: DateTime @timestamp(operations: [UPDATE])
}
type Post {
id: ID! @id
title: String!
content: String!
blog: Blog @relationship(type: "HAS_POST", direction: IN)
comments: [Comment] @relationship(type: "HAS_COMMENT", direction: OUT)
author: User @relationship(type: "WROTE", direction: IN)
createdAt: DateTime @timestamp(operations: [CREATE])
updatedAt: DateTime @timestamp(operations: [UPDATE])
}
type Comment {
id: ID! @id
author: User @relationship(type: "COMMENTED", direction: IN)
content: String!
post: Post @relationship(type: "HAS_COMMENT", direction: IN)
createdAt: DateTime @timestamp(operations: [CREATE])
updatedAt: DateTime @timestamp(operations: [UPDATE])
}
```
> Schema above simplified for clarity.
## Getting Started
If you want to run this Blog locally follow the steps below. When it comes to [Configure environment variables](#how-to-configure-environment-variables-?) you will need a [running Neo4j instance](#how-to-start-neo4j-?) to point to.
### How to configure environment variables ?
Each client and server folders contains a `./env.example` file. Copy this file, to the same directory, at `./.env` and adjust configuration to suit your local machine although the defaults may be fine.
### How to start Neo4j ?
There are many ways to get started with neo4j such as; [Neo4j Sandbox](https://neo4j.com/sandbox/), [Neo4j Desktop](https://neo4j.com/developer/neo4j-desktop/) or [Docker](https://neo4j.com/developer/docker/).
### Steps
Clone the repo;
```
$ git clone https://github.com/neo4j/graphql
```
Install
```
$ cd graphql && yarn install
```
=> [Configure environment variables](#how-to-configure-environment-variables-) <=
Run Seeder on;
```
$ yarn run neo-push:seed
```
> Checkout the seeder its using the OGM
**Once seeded used the default credentials to log in**
1. Email: admin@admin.com
2. Password: password
Run the webpack and graphql servers with;
```
$ yarn run neo-push
```
Navigate to http://localhost:4000 and sign up!
![sign up image](assets/sign-up-screenshot.jpg)
## Authentication
This application has two custom resolvers; sign in and sign up. In the resolvers we return a [JWT](https://jwt.io/). This JWT is stored in local storage on the client. The contents of the JWT is something like;
```
{
"sub": "1234-4321-abcd-dcba", # user.id
"iat": { ... }
}
```
the `.sub` property is the users id. We use `NEO4J_GRAPHQL_JWT_SECRET` env var on the sever to configure the secret.
> Note to keep things simple... This application has no JWT expiry or refreshing mechanism. Patterns you would implement outside of `@neo4j/graphql` so we deemed it less important in this showcase.
When the client is making a request to server we attach the JWT in the `authorization` header of the request, the same header `@neo4j/graphql` looks at.
## Users
At the core of the app but to keep things simple the UI doesn't have any profile page ect ect.
## Blogs
Before you can create a post you must create a blog. Users can have many blogs with many post. Each blog can have an array of authors, whom can post to the blog.
### Dashboard
Once logged in users are directed to the dashboard page;
![dashboard](assets/dashboard.jpg)
```graphql
query myBlogs($id: ID, $offset: Int, $limit: Int, $hasNextBlogsoffset: Int) {
myBlogs: blogs(
where: { OR: [{ creator: { id: $id } }, { authors: { id: $id } }] }
options: { limit: $limit, offset: $offset, sort: { createdAt: DESC } }
) {
id
name
creator {
id
email
}
createdAt
}
hasNextBlogs: blogs(
where: { OR: [{ creator: { id: $id } }, { authors: { id: $id } }] }
options: {
limit: 1
offset: $hasNextBlogsoffset
sort: { createdAt: DESC }
}
) {
id
createdAt
}
}
```
### Pagination
⚠ Page info such as Relay spec is not supported in the current version of `@neo4j/graphql` so with the **My Blogs** and **Recently Updated Blogs** we query twice asking for the next item, to determine if there is a next page. Using this technique we can paginate the blog lists.
> Image showing pagination with limit of 1, in the app its default to 10.
> ![blogs pagination](assets/blog-pagination.gif)
### Create Blog
From the dashboard you can create a blog.
![create blog gif](assets/create-blog.gif)
```graphql
mutation($name: String!, $sub: ID) {
createBlogs(
input: [
{
name: $name
creator: { connect: { where: { node: { id: $sub } } } }
}
]
) {
blogs {
id
name
createdAt
}
}
}
```
### Edit Blog
If your the creator of a blog you can edit its name.
![edit blog gif](assets/edit-blog.gif)
```graphql
mutation editBlog($id: ID, $name: String) {
updateBlogs(where: { id: $id }, update: { name: $name }) {
blogs {
id
}
}
}
```
### Assign Author
If you are the creator of a blog you can assign other users as an author. You can also revoke too!
![assign blog author gif](assets/assign-blog-author.gif)
```graphql
mutation assignBlogAuthor($blog: ID, $authorEmail: String) {
updateBlogs(
where: { id: $blog }
connect: { authors: { where: { node: { email: $authorEmail } } } }
) {
blogs {
authors {
email
}
}
}
}
```
```graphql
mutation revokeBlogAuthor($blog: ID, $authorEmail: String) {
updateBlogs(
where: { id: $blog }
disconnect: { authors: { where: { email: $authorEmail } } }
) {
blogs {
authors {
email
}
}
}
}
```
### Delete Blog
If you are the creator of a blog you can delete it.
![delete blog gif](assets/delete-blog.gif)
```graphql
mutation deleteBlog($id: ID) {
deleteComments(where: { post: { blog: { id: $id } } }) {
nodesDeleted
}
deletePosts(where: { blog: { id: $id } }) {
nodesDeleted
}
deleteBlogs(where: { id: $id }) {
nodesDeleted
}
}
```
## Posts
Users can have many posts with many comments. Blog creators and authors can edit the post. Blog creators and authors of the post can delete it.
### Create Post
Once you have a blog. Either the creator or authors can create a post.
![create post gif](assets/create-post.gif)
> Posts support markdown
```graphql
mutation createPost($title: String!, $content: String!, $user: ID, $blog: ID) {
cre
没有合适的资源?快使用搜索试试~ 我知道了~
Neo4j GraphQL 库(graphql--neo4j-introspector-1.0.1.tar.gz)
1.该资源内容由用户上传,如若侵权请联系客服进行举报
2.虚拟产品一经售出概不退款(资源遇到问题,请及时私信上传者)
2.虚拟产品一经售出概不退款(资源遇到问题,请及时私信上传者)
版权申诉
0 下载量 145 浏览量
2022-01-15
17:26:02
上传
评论
收藏 6.3MB GZ 举报
温馨提示
共892个文件
ts:630个
adoc:78个
md:35个
Neo4j GraphQL 库(graphql--neo4j-introspector-1.0.1.tar.gz) 源代码。 Neo4j GraphQL 库是一个高度灵活、低代码、开源的 JavaScript 库,可通过利用连接数据的力量为跨平台和移动应用程序实现快速 API 开发。 使用 Neo4j 作为图形数据库,GraphQL 库使应用程序可以轻松地将应用程序数据从前端一直到存储都视为原生图形,避免重复的模式工作并确保前端和后端开发人员之间的完美集成. 该库的模式优先范式以 TypeScript 编写,让开发人员可以专注于他们需要的应用程序数据,同时负责构建 API 所涉及的繁重工作。
资源推荐
资源详情
资源评论
收起资源包目录
Neo4j GraphQL 库(graphql--neo4j-introspector-1.0.1.tar.gz) (892个子文件)
interfaces.adoc 9KB
types.adoc 9KB
mutations.adoc 9KB
neo4jgraphql.adoc 8KB
relationships.adoc 7KB
filtering.adoc 7KB
getting-started.adoc 7KB
setup.adoc 6KB
indexes-and-constraints.adoc 6KB
driver-configuration.adoc 6KB
type-definitions.adoc 6KB
mutations.adoc 5KB
cypher.adoc 5KB
queries.adoc 5KB
introduction.adoc 5KB
database-mapping.adoc 5KB
queries.adoc 4KB
selection-set.adoc 4KB
custom-resolvers.adoc 4KB
directives.adoc 4KB
update.adoc 4KB
create.adoc 4KB
unions.adoc 4KB
allow.adoc 4KB
autogeneration.adoc 3KB
introspector.adoc 3KB
access-control.adoc 3KB
bind.adoc 3KB
content-nav.adoc 3KB
miscellaneous.adoc 3KB
unions.adoc 3KB
index.adoc 3KB
delete.adoc 3KB
index.adoc 3KB
server.adoc 2KB
cursor-based.adoc 2KB
rest-api.adoc 2KB
type-generation.adoc 2KB
update.adoc 2KB
nextjs.adoc 2KB
auth-directive.adoc 2KB
default-values.adoc 2KB
custom-resolvers.adoc 2KB
basics.adoc 2KB
faqs.adoc 2KB
authentication.adoc 2KB
offset-based.adoc 2KB
index.adoc 2KB
preventing-overfetching.adoc 2KB
private.adoc 2KB
sorting.adoc 2KB
find.adoc 1KB
roles.adoc 1KB
index.adoc 1KB
index.adoc 1KB
delete.adoc 1KB
index.adoc 1KB
index.adoc 1KB
type-generation.adoc 1KB
create.adoc 1KB
aggregate.adoc 943B
installation.adoc 939B
ogm.adoc 923B
index.adoc 861B
where.adoc 773B
count.adoc 710B
index.adoc 540B
security.adoc 467B
index.adoc 464B
index.adoc 381B
index.adoc 380B
index.adoc 354B
README.adoc 278B
notes.adoc 251B
index.adoc 200B
index.adoc 190B
index.adoc 145B
ogm.adoc 91B
.babelrc 41B
yarn-3.1.1.cjs 2.1MB
plugin-version.cjs 1.02MB
plugin-workspace-tools.cjs 51KB
plugin-typescript.cjs 34KB
graphql.code-snippets 2KB
main.css 1KB
Dockerfile 490B
.dockerignore 43B
.editorconfig 294B
.eslintignore 44B
.env.example 161B
.env.example 96B
env.example 76B
overview.gif 909KB
assign-blog-author.gif 403KB
create-post.gif 390KB
create-comment.gif 355KB
create-blog.gif 348KB
delete-blog.gif 343KB
delete-post.gif 339KB
delete-comment.gif 230KB
共 892 条
- 1
- 2
- 3
- 4
- 5
- 6
- 9
资源评论
YunFeiDong
- 粉丝: 33
- 资源: 3849
下载权益
C知道特权
VIP文章
课程特权
开通VIP
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功