├── .gitignore
├── README.md
├── blogPart1.txt
├── blogPart2.txt
├── channel.sql
├── golang
├── .realize.yaml
├── app
│ ├── config
│ │ ├── connection
│ │ │ └── connection.go
│ │ ├── constants
│ │ │ └── constants.go
│ │ └── database
│ │ │ └── database.go
│ ├── graph
│ │ └── generated.go
│ ├── model
│ │ └── models_gen.go
│ └── resolver
│ │ ├── ChannelResolver.go
│ │ └── resolver.go
├── gqlgen.yml
├── main.go
└── schema.graphql
└── reactjs
├── package.json
├── public
├── css
│ ├── bootstrap.min.css
│ ├── dataTables.bootstrap4.min.css
│ ├── datatables.min.css
│ └── loader.css
├── img
│ ├── 3pl-logo-600.png
│ ├── favicon-16x16.png
│ ├── favicon-32x32.png
│ ├── green.png
│ ├── red.png
│ ├── yellow.jpg
│ └── yellow.png
├── index.html
└── js
│ ├── bootstrap.min.js
│ ├── dataTables.bootstrap4.min.js
│ ├── datatables.min.js
│ ├── jquery-3.2.1.min.js
│ ├── jquery.dataTables.min.js
│ └── jquery.validate.min.js
└── src
├── App.jsx
├── components
└── ChannelList
│ ├── ChannelList.css
│ └── ChannelList.jsx
├── environment.jsx
├── index.js
└── style
└── app.scss
/.gitignore:
--------------------------------------------------------------------------------
1 | # See https://help.github.com/ignore-files/ for more about ignoring files.
2 |
3 | # dependencies
4 | reactjs/node_modules
5 |
6 | # testing
7 | /coverage
8 |
9 | # production
10 | /build
11 |
12 | package-lock.json
13 |
14 | # misc
15 | .DS_Store
16 | .env.local
17 | .env.development.local
18 | .env.test.local
19 | .env.production.local
20 |
21 | npm-debug.log*
22 | yarn-debug.log*
23 | yarn-error.log*
24 |
25 |
26 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Golang-gqlgen-Reactjs-subscription-demo
2 |
3 | You can find step by step guide for Golang Part 1 [here](https://www.logisticinfotech.com/blog/graphql-subscription-golang-reactjs/) And React Part 2 [here](https://www.logisticinfotech.com/blog/react-apollo-client-subscription/) to understand this demo properly.
4 |
5 | for golang graphql gqlgen package is used.
6 | for reacjs applo-client is used.
7 |
8 | ## Preview
9 | 
10 |
11 | ## How to Run
12 | ```
13 | cd golang
14 | go get ./
15 | go run main.go
16 |
17 | cd reactjs
18 | npm install
19 | npm start
20 |
21 | ```
22 |
23 | Golang graphql server will start on
24 | http://localhost:8888
25 |
26 | React server will start on
27 | http://localhost:3000
28 |
29 |
30 |
31 | ## Further help
32 |
33 | Checkout full blog for Golang Part 1 [here](https://www.logisticinfotech.com/blog/graphql-subscription-golang-reactjs/) And React Part 2 [here](https://www.logisticinfotech.com/blog/react-apollo-client-subscription/)
34 |
--------------------------------------------------------------------------------
/blogPart1.txt:
--------------------------------------------------------------------------------
1 | For this demo we have used golang gqlgen package, mysql and reactjs apollo-client.
2 | For better understanding we have used mysql for database.
3 | Purpose of this demo is to showcase graphql query, mutation and subscription in golang.
4 | Although gqlgen original documantation is good but I thought its best to do CRUD saperatly for learning purpose.
5 | I hope this will great help to someone starting golang graphql.
6 | I am considering reader has little knowledge of golang and database connection in golang
7 |
8 | This is part1 of two searies tutorial
9 | 1. golang gqlgen backend
10 | 2. reactjs apollo-client front end which using this golang backend.
11 |
12 | what is gqlgen?
13 | Its golang package cum utility which allows us to auto generate golang code stub from graphql schema automatically.
14 | Their original getting started is good to read but I will mention steps here also.
15 |
16 | Step 1 :
17 | > Install gqlgen
18 | $ go get -u github.com/99designs/gqlgen github.com/vektah/gorunpkg
19 |
20 | > All the code we will be doing should reside in go/src folder.
21 | So purpose of this demo
22 | ~/go/src/golang-gqlgen-reactjs-subscription-demo/golang
23 | this is preferred path.
24 |
25 |
26 | Step 2:
27 | so first we need to create our required graphql schema.
28 |
29 | Create schema.graphql file with below:
30 | type Channel {
31 | id: Int! # "!" denotes a required field
32 | name: String!
33 | }
34 |
35 | type Query {
36 | channels: [Channel!]!
37 | }
38 |
39 | type Mutation {
40 | addChannel(name: String!): Channel!
41 | updateChannel(id:Int!,name: String!): Channel!
42 | deleteChannel(ID: Int!): Channel!
43 | }
44 |
45 | type Subscription {
46 | subscriptionChannelAdded: Channel!
47 | subscriptionChannelDeleted: Channel!
48 | subscriptionChannelUpdated: Channel!
49 | }
50 |
51 | then next file we need is gqlgen.yml
52 | this file is responsible to direct gqlgen where to autogenerate files.
53 |
54 | for our demo purpose content will be as below
55 | schema: schema.graphql
56 | exec:
57 | filename: app/graph/generated.go
58 |
59 | model:
60 | filename: app/model/models_gen.go
61 |
62 | resolver:
63 | filename: app/resolver/resolver.go
64 | type: Resolver
65 |
66 | Step 3:
67 | inside our mentioned folder fire command
68 | $ gqlgen
69 |
70 | this will generate below files if you are first time running it.
71 |
72 | app/graph/generated.go
73 | app/model/models_gen.go
74 | app/resolver/resolver.go (if this file exists it will not be regenrated)
75 |
76 | Step 4:
77 | So first thing will require for us is graphql query to get all channels.
78 |
79 | As we have followed little different structure for ease of understanding and maintanance.
80 | Create file app/resolver/ChannelResolver.go
81 |
82 | func (r *queryResolver) Channels(ctx context.Context) ([]model.Channel, error) {
83 | db := connection.DbConn()
84 | var query = "SELECT * FROM channel"
85 | selDB, err := db.Query(query)
86 | var arrChannel []model.Channel
87 | for selDB.Next() {
88 | var name string
89 | var id int64
90 | err = selDB.Scan(&id, &name)
91 | if err != nil {
92 | panic(err.Error())
93 | }
94 | todo1 := model.Channel{ID: int(id), Name: name}
95 | arrChannel = append(arrChannel, todo1)
96 | }
97 |
98 | defer db.Close()
99 | return arrChannel, nil
100 | }
101 |
102 | dont forget to remove below funciton from resolver.go file
103 | Channels(ctx context.Context) ([]model.Channel, error)
104 |
105 | For now we will consontrate only on Add Channel Mutation and Subscription
106 | (although we have included Edit/Delete Channels mutation and subscription)
107 |
108 | For subscription we need to create one observer for our channel list
109 | var addChannelObserver map[string]chan model.Channel
110 |
111 | Now in ChannelResolver.go init we set blank model.Channel Object in addChannelObserver
112 | func init() {
113 | addChannelObserver = map[string]chan model.Channel{}
114 | }
115 |
116 | When any new channel added we need to add newly added channel into our addChannelObserver
117 |
118 | func (r *mutationResolver) AddChannel(ctx context.Context, name string) (model.Channel, error) {
119 | db := connection.DbConn()
120 |
121 | insForm, err := db.Prepare("INSERT INTO channel(name) VALUES(?)")
122 | if err != nil {
123 | panic(err.Error())
124 | }
125 |
126 | var newChannel model.Channel
127 | res, err := insForm.Exec(name)
128 | if err != nil {
129 | println("Exec err:", err.Error())
130 | } else {
131 | var id int64
132 | id, err := res.LastInsertId()
133 | if err != nil {
134 | println("Error:", err.Error())
135 | } else {
136 | newChannel = model.Channel{ID: int(id), Name: name}
137 | }
138 | }
139 | defer db.Close()
140 | // Add new chanel in addChannelObserver
141 | for _, observer := range addChannelObserver {
142 | observer <- newChannel
143 | }
144 | return newChannel, nil
145 | }
146 |
147 | Now we will create function to fire subscription for channelAdded
148 |
149 | func (r *subscriptionResolver) SubscriptionChannelAdded(ctx context.Context) (<-chan model.Channel, error) {
150 | id := randString(8)
151 | events := make(chan model.Channel, 1)
152 |
153 | go func() {
154 | <-ctx.Done()
155 | delete(addChannelObserver, id)
156 | }()
157 |
158 | addChannelObserver[id] = events
159 |
160 | return events, nil
161 | }
162 |
163 | We can run this code with
164 | $ go run main.go
165 |
166 | and url will be http://localhost:8888
167 |
168 | That is all for golang code
169 |
--------------------------------------------------------------------------------
/blogPart2.txt:
--------------------------------------------------------------------------------
1 | This is a second part of reactjs apollo-client front end in which as backend we have used golang gqlgen graphql server
2 | Here also I am assuming readers know reactjs little bit.
3 |
4 | For this demo again preferred path is
5 | ~/go/src/golang-gqlgen-reactjs-subscription-demo/reactjs
6 |
7 | Step 1 :
8 | you can start react project with default create-react-app
9 |
10 | First of all we need to connect our front-end with back end
11 | So we have used ApolloClient for connection to golang backend
12 |
13 | const wsLink = new WebSocketLink({
14 | uri: environment.WSHost,
15 | options: {
16 | reconnect: true
17 | }
18 | });
19 | const apolloClient = new ApolloClient({
20 | link: wsLink,
21 | cache: new InMemoryCache(),
22 | });
23 |
24 | function render(component) {
25 | ReactDOM.render(
26 | {component}
27 | , document.getElementById('root'));
28 | }
29 |
30 | render();
31 |
32 | Step 2:
33 | Create component for CURD operation of channel
34 | for that we will create file reactjs/src/components/ChannelList.jsx
35 |
36 | Okay so we will try to understand devide this file in few section to understand easily
37 | 1) Import section we need to insert react-apollo and graphql-tag for call graphql Query and Mutation
38 | import React, { Component } from 'react';
39 | import { graphql, Mutation, compose } from 'react-apollo';
40 | import gql from 'graphql-tag';
41 |
42 | 2) Render of react component
43 | class ChannelsList extends Component {
44 | componentWillMount() {
45 | // Add subscribeToMore method for watch subscription of add channel
46 | this.props.data.subscribeToMore({
47 | document: addChannelSubscription, // Use the subscription
48 | updateQuery: (prev, { subscriptionData }) => {
49 | if (!subscriptionData.data) {
50 | return prev;
51 | }
52 | const newChannel = subscriptionData.data.subscriptionChannelAdded;
53 | // Add check to prevent double adding of channels.
54 | if (!prev.channels.find((channel) => channel.id === newChannel.id)) {
55 | let updatedChannels = Object.assign({}, prev, { channels: [...prev.channels, newChannel] });
56 | return updatedChannels;
57 | } else {
58 | return prev;
59 | }
60 | }
61 | });
62 | }
63 |
64 | render() {
65 | // we get data of channels on page render from props
66 | const { data: { loading, error, channels } } = this.props;
67 | if (loading) {
68 | return
Loading ...
;
69 | }
70 | if (error) {
71 | return {error.message}
;
72 | }
73 |
74 | return (
75 |
76 |
77 |
78 |
Channel List
79 |
80 |
81 |
88 |
89 |
90 | {channels.map(ch =>
91 | -
92 |
95 |
104 |
105 | )}
106 |
107 |
108 |
109 |
110 | )
111 | }
112 | }
113 |
114 | 3) Now Write Query ,Mutation and Subscription for CRUD channel
115 | // query for get all channel list
116 | export const channelsListQuery = gql`
117 | query ChannelsListQuery {
118 | channels {
119 | id
120 | name
121 | }
122 | }
123 | `;
124 |
125 | //Mutation for add channel
126 | const CreateChannelMutation = gql`
127 | mutation addChannel($name: String!) {
128 | addChannel(name: $name) {
129 | id
130 | name
131 | }
132 | }
133 | `;
134 |
135 | //Subscription for newly added channel
136 |
137 | const addChannelSubscription = gql`
138 | subscription Channels {
139 | subscriptionChannelAdded {
140 | id
141 | name
142 | }
143 | }
144 | `
145 |
146 | //export class with graphql query and mutation is very import for get data on component load
147 |
148 | const multipleMutation = compose(
149 | graphql(CreateChannelMutation, { name: 'createChannelMutation' })
150 | )
151 | export default compose(multipleMutation, graphql(channelsListQuery))(ChannelsList);
152 |
--------------------------------------------------------------------------------
/channel.sql:
--------------------------------------------------------------------------------
1 | -- phpMyAdmin SQL Dump
2 | -- version 4.5.4.1deb2ubuntu2
3 | -- http://www.phpmyadmin.net
4 | --
5 | -- Host: localhost
6 | -- Generation Time: Sep 13, 2018 at 05:12 PM
7 | -- Server version: 5.7.19-0ubuntu0.16.04.1
8 | -- PHP Version: 7.0.22-0ubuntu0.16.04.1
9 |
10 | SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
11 |
12 |
13 | /*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
14 | /*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
15 | /*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
16 | /*!40101 SET NAMES utf8mb4 */;
17 |
18 | --
19 | -- Database: `gqlgenreact`
20 | --
21 |
22 | -- --------------------------------------------------------
23 |
24 | --
25 | -- Table structure for table `channel`
26 | --
27 |
28 | CREATE TABLE `channel` (
29 | `id` int(11) NOT NULL,
30 | `name` varchar(255) NOT NULL
31 | ) ENGINE=InnoDB DEFAULT CHARSET=latin1;
32 |
33 | --
34 | -- Indexes for dumped tables
35 | --
36 |
37 | --
38 | -- Indexes for table `channel`
39 | --
40 | ALTER TABLE `channel`
41 | ADD PRIMARY KEY (`id`);
42 |
43 | --
44 | -- AUTO_INCREMENT for dumped tables
45 | --
46 |
47 | --
48 | -- AUTO_INCREMENT for table `channel`
49 | --
50 | ALTER TABLE `channel`
51 | MODIFY `id` int(11) NOT NULL AUTO_INCREMENT;
52 | /*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
53 | /*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
54 | /*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
55 |
--------------------------------------------------------------------------------
/golang/.realize.yaml:
--------------------------------------------------------------------------------
1 | settings:
2 | legacy:
3 | force: false
4 | interval: 0s
5 | schema:
6 | - name: gqlgen_demo
7 | path: .
8 | commands:
9 | run:
10 | status: true
11 | watcher:
12 | extensions:
13 | - go
14 | paths:
15 | - /
16 | ignored_paths:
17 | - .git
18 | - .realize
19 | - vendor
20 |
--------------------------------------------------------------------------------
/golang/app/config/connection/connection.go:
--------------------------------------------------------------------------------
1 | package connection
2 |
3 | import (
4 | "database/sql"
5 | "lidemo/gqlgenreact/golang/app/config/constants"
6 |
7 | _ "github.com/go-sql-driver/mysql"
8 | )
9 |
10 | func DbConn() (db *sql.DB) {
11 | dbDriver := "mysql"
12 | dbUser := constants.DBUSER
13 | dbPass := constants.DBPASSWORD
14 | dbHost := constants.DBHOST
15 | dbPort := constants.DBPORT
16 | dbName := constants.DBNAME
17 | db, err := sql.Open(dbDriver, dbUser+":"+dbPass+"@tcp("+dbHost+":"+dbPort+")/"+dbName+"?parseTime=true")
18 | if err != nil {
19 | panic(err.Error())
20 | }
21 | return db
22 | }
23 |
--------------------------------------------------------------------------------
/golang/app/config/constants/constants.go:
--------------------------------------------------------------------------------
1 | package constants
2 |
3 | const (
4 | DBUSER = "gqlgenreact"
5 | DBPASSWORD = "gqlgenreact"
6 | DBHOST = "192.168.0.77"
7 | DBPORT = "3306"
8 | DBNAME = "gqlgenreact"
9 | )
10 |
--------------------------------------------------------------------------------
/golang/app/config/database/database.go:
--------------------------------------------------------------------------------
1 | package database
2 |
3 | import "github.com/jinzhu/gorm"
4 |
5 | var (
6 | // DBCon is the connection handle
7 | // for the database
8 | DBCon *gorm.DB
9 | )
10 |
--------------------------------------------------------------------------------
/golang/app/graph/generated.go:
--------------------------------------------------------------------------------
1 | // Code generated by github.com/99designs/gqlgen, DO NOT EDIT.
2 |
3 | package graph
4 |
5 | import (
6 | "bytes"
7 | context "context"
8 | model "golang-gqlgen-reactjs-subscription-demo/golang/app/model"
9 | strconv "strconv"
10 | sync "sync"
11 |
12 | graphql "github.com/99designs/gqlgen/graphql"
13 | introspection "github.com/99designs/gqlgen/graphql/introspection"
14 | gqlparser "github.com/vektah/gqlparser"
15 | ast "github.com/vektah/gqlparser/ast"
16 | )
17 |
18 | // NewExecutableSchema creates an ExecutableSchema from the ResolverRoot interface.
19 | func NewExecutableSchema(cfg Config) graphql.ExecutableSchema {
20 | return &executableSchema{
21 | resolvers: cfg.Resolvers,
22 | directives: cfg.Directives,
23 | complexity: cfg.Complexity,
24 | }
25 | }
26 |
27 | type Config struct {
28 | Resolvers ResolverRoot
29 | Directives DirectiveRoot
30 | Complexity ComplexityRoot
31 | }
32 |
33 | type ResolverRoot interface {
34 | Mutation() MutationResolver
35 | Query() QueryResolver
36 | Subscription() SubscriptionResolver
37 | }
38 |
39 | type DirectiveRoot struct {
40 | }
41 |
42 | type ComplexityRoot struct {
43 | Channel struct {
44 | Id func(childComplexity int) int
45 | Name func(childComplexity int) int
46 | }
47 |
48 | Mutation struct {
49 | AddChannel func(childComplexity int, name string) int
50 | UpdateChannel func(childComplexity int, id int, name string) int
51 | DeleteChannel func(childComplexity int, ID int) int
52 | }
53 |
54 | Query struct {
55 | Channels func(childComplexity int) int
56 | }
57 |
58 | Subscription struct {
59 | SubscriptionChannelAdded func(childComplexity int) int
60 | SubscriptionChannelDeleted func(childComplexity int) int
61 | SubscriptionChannelUpdated func(childComplexity int) int
62 | }
63 | }
64 |
65 | type MutationResolver interface {
66 | AddChannel(ctx context.Context, name string) (model.Channel, error)
67 | UpdateChannel(ctx context.Context, id int, name string) (model.Channel, error)
68 | DeleteChannel(ctx context.Context, ID int) (model.Channel, error)
69 | }
70 | type QueryResolver interface {
71 | Channels(ctx context.Context) ([]model.Channel, error)
72 | }
73 | type SubscriptionResolver interface {
74 | SubscriptionChannelAdded(ctx context.Context) (<-chan model.Channel, error)
75 | SubscriptionChannelDeleted(ctx context.Context) (<-chan model.Channel, error)
76 | SubscriptionChannelUpdated(ctx context.Context) (<-chan model.Channel, error)
77 | }
78 |
79 | func field_Mutation_addChannel_args(rawArgs map[string]interface{}) (map[string]interface{}, error) {
80 | args := map[string]interface{}{}
81 | var arg0 string
82 | if tmp, ok := rawArgs["name"]; ok {
83 | var err error
84 | arg0, err = graphql.UnmarshalString(tmp)
85 | if err != nil {
86 | return nil, err
87 | }
88 | }
89 | args["name"] = arg0
90 | return args, nil
91 |
92 | }
93 |
94 | func field_Mutation_updateChannel_args(rawArgs map[string]interface{}) (map[string]interface{}, error) {
95 | args := map[string]interface{}{}
96 | var arg0 int
97 | if tmp, ok := rawArgs["id"]; ok {
98 | var err error
99 | arg0, err = graphql.UnmarshalInt(tmp)
100 | if err != nil {
101 | return nil, err
102 | }
103 | }
104 | args["id"] = arg0
105 | var arg1 string
106 | if tmp, ok := rawArgs["name"]; ok {
107 | var err error
108 | arg1, err = graphql.UnmarshalString(tmp)
109 | if err != nil {
110 | return nil, err
111 | }
112 | }
113 | args["name"] = arg1
114 | return args, nil
115 |
116 | }
117 |
118 | func field_Mutation_deleteChannel_args(rawArgs map[string]interface{}) (map[string]interface{}, error) {
119 | args := map[string]interface{}{}
120 | var arg0 int
121 | if tmp, ok := rawArgs["ID"]; ok {
122 | var err error
123 | arg0, err = graphql.UnmarshalInt(tmp)
124 | if err != nil {
125 | return nil, err
126 | }
127 | }
128 | args["ID"] = arg0
129 | return args, nil
130 |
131 | }
132 |
133 | func field_Query___type_args(rawArgs map[string]interface{}) (map[string]interface{}, error) {
134 | args := map[string]interface{}{}
135 | var arg0 string
136 | if tmp, ok := rawArgs["name"]; ok {
137 | var err error
138 | arg0, err = graphql.UnmarshalString(tmp)
139 | if err != nil {
140 | return nil, err
141 | }
142 | }
143 | args["name"] = arg0
144 | return args, nil
145 |
146 | }
147 |
148 | func field___Type_fields_args(rawArgs map[string]interface{}) (map[string]interface{}, error) {
149 | args := map[string]interface{}{}
150 | var arg0 bool
151 | if tmp, ok := rawArgs["includeDeprecated"]; ok {
152 | var err error
153 | arg0, err = graphql.UnmarshalBoolean(tmp)
154 | if err != nil {
155 | return nil, err
156 | }
157 | }
158 | args["includeDeprecated"] = arg0
159 | return args, nil
160 |
161 | }
162 |
163 | func field___Type_enumValues_args(rawArgs map[string]interface{}) (map[string]interface{}, error) {
164 | args := map[string]interface{}{}
165 | var arg0 bool
166 | if tmp, ok := rawArgs["includeDeprecated"]; ok {
167 | var err error
168 | arg0, err = graphql.UnmarshalBoolean(tmp)
169 | if err != nil {
170 | return nil, err
171 | }
172 | }
173 | args["includeDeprecated"] = arg0
174 | return args, nil
175 |
176 | }
177 |
178 | type executableSchema struct {
179 | resolvers ResolverRoot
180 | directives DirectiveRoot
181 | complexity ComplexityRoot
182 | }
183 |
184 | func (e *executableSchema) Schema() *ast.Schema {
185 | return parsedSchema
186 | }
187 |
188 | func (e *executableSchema) Complexity(typeName, field string, childComplexity int, rawArgs map[string]interface{}) (int, bool) {
189 | switch typeName + "." + field {
190 |
191 | case "Channel.id":
192 | if e.complexity.Channel.Id == nil {
193 | break
194 | }
195 |
196 | return e.complexity.Channel.Id(childComplexity), true
197 |
198 | case "Channel.name":
199 | if e.complexity.Channel.Name == nil {
200 | break
201 | }
202 |
203 | return e.complexity.Channel.Name(childComplexity), true
204 |
205 | case "Mutation.addChannel":
206 | if e.complexity.Mutation.AddChannel == nil {
207 | break
208 | }
209 |
210 | args, err := field_Mutation_addChannel_args(rawArgs)
211 | if err != nil {
212 | return 0, false
213 | }
214 |
215 | return e.complexity.Mutation.AddChannel(childComplexity, args["name"].(string)), true
216 |
217 | case "Mutation.updateChannel":
218 | if e.complexity.Mutation.UpdateChannel == nil {
219 | break
220 | }
221 |
222 | args, err := field_Mutation_updateChannel_args(rawArgs)
223 | if err != nil {
224 | return 0, false
225 | }
226 |
227 | return e.complexity.Mutation.UpdateChannel(childComplexity, args["id"].(int), args["name"].(string)), true
228 |
229 | case "Mutation.deleteChannel":
230 | if e.complexity.Mutation.DeleteChannel == nil {
231 | break
232 | }
233 |
234 | args, err := field_Mutation_deleteChannel_args(rawArgs)
235 | if err != nil {
236 | return 0, false
237 | }
238 |
239 | return e.complexity.Mutation.DeleteChannel(childComplexity, args["ID"].(int)), true
240 |
241 | case "Query.channels":
242 | if e.complexity.Query.Channels == nil {
243 | break
244 | }
245 |
246 | return e.complexity.Query.Channels(childComplexity), true
247 |
248 | case "Subscription.subscriptionChannelAdded":
249 | if e.complexity.Subscription.SubscriptionChannelAdded == nil {
250 | break
251 | }
252 |
253 | return e.complexity.Subscription.SubscriptionChannelAdded(childComplexity), true
254 |
255 | case "Subscription.subscriptionChannelDeleted":
256 | if e.complexity.Subscription.SubscriptionChannelDeleted == nil {
257 | break
258 | }
259 |
260 | return e.complexity.Subscription.SubscriptionChannelDeleted(childComplexity), true
261 |
262 | case "Subscription.subscriptionChannelUpdated":
263 | if e.complexity.Subscription.SubscriptionChannelUpdated == nil {
264 | break
265 | }
266 |
267 | return e.complexity.Subscription.SubscriptionChannelUpdated(childComplexity), true
268 |
269 | }
270 | return 0, false
271 | }
272 |
273 | func (e *executableSchema) Query(ctx context.Context, op *ast.OperationDefinition) *graphql.Response {
274 | ec := executionContext{graphql.GetRequestContext(ctx), e}
275 |
276 | buf := ec.RequestMiddleware(ctx, func(ctx context.Context) []byte {
277 | data := ec._Query(ctx, op.SelectionSet)
278 | var buf bytes.Buffer
279 | data.MarshalGQL(&buf)
280 | return buf.Bytes()
281 | })
282 |
283 | return &graphql.Response{
284 | Data: buf,
285 | Errors: ec.Errors,
286 | }
287 | }
288 |
289 | func (e *executableSchema) Mutation(ctx context.Context, op *ast.OperationDefinition) *graphql.Response {
290 | ec := executionContext{graphql.GetRequestContext(ctx), e}
291 |
292 | buf := ec.RequestMiddleware(ctx, func(ctx context.Context) []byte {
293 | data := ec._Mutation(ctx, op.SelectionSet)
294 | var buf bytes.Buffer
295 | data.MarshalGQL(&buf)
296 | return buf.Bytes()
297 | })
298 |
299 | return &graphql.Response{
300 | Data: buf,
301 | Errors: ec.Errors,
302 | }
303 | }
304 |
305 | func (e *executableSchema) Subscription(ctx context.Context, op *ast.OperationDefinition) func() *graphql.Response {
306 | ec := executionContext{graphql.GetRequestContext(ctx), e}
307 |
308 | next := ec._Subscription(ctx, op.SelectionSet)
309 | if ec.Errors != nil {
310 | return graphql.OneShot(&graphql.Response{Data: []byte("null"), Errors: ec.Errors})
311 | }
312 |
313 | var buf bytes.Buffer
314 | return func() *graphql.Response {
315 | buf := ec.RequestMiddleware(ctx, func(ctx context.Context) []byte {
316 | buf.Reset()
317 | data := next()
318 |
319 | if data == nil {
320 | return nil
321 | }
322 | data.MarshalGQL(&buf)
323 | return buf.Bytes()
324 | })
325 |
326 | return &graphql.Response{
327 | Data: buf,
328 | Errors: ec.Errors,
329 | }
330 | }
331 | }
332 |
333 | type executionContext struct {
334 | *graphql.RequestContext
335 | *executableSchema
336 | }
337 |
338 | var channelImplementors = []string{"Channel"}
339 |
340 | // nolint: gocyclo, errcheck, gas, goconst
341 | func (ec *executionContext) _Channel(ctx context.Context, sel ast.SelectionSet, obj *model.Channel) graphql.Marshaler {
342 | fields := graphql.CollectFields(ctx, sel, channelImplementors)
343 |
344 | out := graphql.NewOrderedMap(len(fields))
345 | invalid := false
346 | for i, field := range fields {
347 | out.Keys[i] = field.Alias
348 |
349 | switch field.Name {
350 | case "__typename":
351 | out.Values[i] = graphql.MarshalString("Channel")
352 | case "id":
353 | out.Values[i] = ec._Channel_id(ctx, field, obj)
354 | if out.Values[i] == graphql.Null {
355 | invalid = true
356 | }
357 | case "name":
358 | out.Values[i] = ec._Channel_name(ctx, field, obj)
359 | if out.Values[i] == graphql.Null {
360 | invalid = true
361 | }
362 | default:
363 | panic("unknown field " + strconv.Quote(field.Name))
364 | }
365 | }
366 |
367 | if invalid {
368 | return graphql.Null
369 | }
370 | return out
371 | }
372 |
373 | // nolint: vetshadow
374 | func (ec *executionContext) _Channel_id(ctx context.Context, field graphql.CollectedField, obj *model.Channel) graphql.Marshaler {
375 | rctx := &graphql.ResolverContext{
376 | Object: "Channel",
377 | Args: nil,
378 | Field: field,
379 | }
380 | ctx = graphql.WithResolverContext(ctx, rctx)
381 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
382 | return obj.ID, nil
383 | })
384 | if resTmp == nil {
385 | if !ec.HasError(rctx) {
386 | ec.Errorf(ctx, "must not be null")
387 | }
388 | return graphql.Null
389 | }
390 | res := resTmp.(int)
391 | rctx.Result = res
392 | return graphql.MarshalInt(res)
393 | }
394 |
395 | // nolint: vetshadow
396 | func (ec *executionContext) _Channel_name(ctx context.Context, field graphql.CollectedField, obj *model.Channel) graphql.Marshaler {
397 | rctx := &graphql.ResolverContext{
398 | Object: "Channel",
399 | Args: nil,
400 | Field: field,
401 | }
402 | ctx = graphql.WithResolverContext(ctx, rctx)
403 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
404 | return obj.Name, nil
405 | })
406 | if resTmp == nil {
407 | if !ec.HasError(rctx) {
408 | ec.Errorf(ctx, "must not be null")
409 | }
410 | return graphql.Null
411 | }
412 | res := resTmp.(string)
413 | rctx.Result = res
414 | return graphql.MarshalString(res)
415 | }
416 |
417 | var mutationImplementors = []string{"Mutation"}
418 |
419 | // nolint: gocyclo, errcheck, gas, goconst
420 | func (ec *executionContext) _Mutation(ctx context.Context, sel ast.SelectionSet) graphql.Marshaler {
421 | fields := graphql.CollectFields(ctx, sel, mutationImplementors)
422 |
423 | ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
424 | Object: "Mutation",
425 | })
426 |
427 | out := graphql.NewOrderedMap(len(fields))
428 | invalid := false
429 | for i, field := range fields {
430 | out.Keys[i] = field.Alias
431 |
432 | switch field.Name {
433 | case "__typename":
434 | out.Values[i] = graphql.MarshalString("Mutation")
435 | case "addChannel":
436 | out.Values[i] = ec._Mutation_addChannel(ctx, field)
437 | if out.Values[i] == graphql.Null {
438 | invalid = true
439 | }
440 | case "updateChannel":
441 | out.Values[i] = ec._Mutation_updateChannel(ctx, field)
442 | if out.Values[i] == graphql.Null {
443 | invalid = true
444 | }
445 | case "deleteChannel":
446 | out.Values[i] = ec._Mutation_deleteChannel(ctx, field)
447 | if out.Values[i] == graphql.Null {
448 | invalid = true
449 | }
450 | default:
451 | panic("unknown field " + strconv.Quote(field.Name))
452 | }
453 | }
454 |
455 | if invalid {
456 | return graphql.Null
457 | }
458 | return out
459 | }
460 |
461 | // nolint: vetshadow
462 | func (ec *executionContext) _Mutation_addChannel(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
463 | rawArgs := field.ArgumentMap(ec.Variables)
464 | args, err := field_Mutation_addChannel_args(rawArgs)
465 | if err != nil {
466 | ec.Error(ctx, err)
467 | return graphql.Null
468 | }
469 | rctx := &graphql.ResolverContext{
470 | Object: "Mutation",
471 | Args: args,
472 | Field: field,
473 | }
474 | ctx = graphql.WithResolverContext(ctx, rctx)
475 | resTmp := ec.FieldMiddleware(ctx, nil, func(ctx context.Context) (interface{}, error) {
476 | return ec.resolvers.Mutation().AddChannel(ctx, args["name"].(string))
477 | })
478 | if resTmp == nil {
479 | if !ec.HasError(rctx) {
480 | ec.Errorf(ctx, "must not be null")
481 | }
482 | return graphql.Null
483 | }
484 | res := resTmp.(model.Channel)
485 | rctx.Result = res
486 |
487 | return ec._Channel(ctx, field.Selections, &res)
488 | }
489 |
490 | // nolint: vetshadow
491 | func (ec *executionContext) _Mutation_updateChannel(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
492 | rawArgs := field.ArgumentMap(ec.Variables)
493 | args, err := field_Mutation_updateChannel_args(rawArgs)
494 | if err != nil {
495 | ec.Error(ctx, err)
496 | return graphql.Null
497 | }
498 | rctx := &graphql.ResolverContext{
499 | Object: "Mutation",
500 | Args: args,
501 | Field: field,
502 | }
503 | ctx = graphql.WithResolverContext(ctx, rctx)
504 | resTmp := ec.FieldMiddleware(ctx, nil, func(ctx context.Context) (interface{}, error) {
505 | return ec.resolvers.Mutation().UpdateChannel(ctx, args["id"].(int), args["name"].(string))
506 | })
507 | if resTmp == nil {
508 | if !ec.HasError(rctx) {
509 | ec.Errorf(ctx, "must not be null")
510 | }
511 | return graphql.Null
512 | }
513 | res := resTmp.(model.Channel)
514 | rctx.Result = res
515 |
516 | return ec._Channel(ctx, field.Selections, &res)
517 | }
518 |
519 | // nolint: vetshadow
520 | func (ec *executionContext) _Mutation_deleteChannel(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
521 | rawArgs := field.ArgumentMap(ec.Variables)
522 | args, err := field_Mutation_deleteChannel_args(rawArgs)
523 | if err != nil {
524 | ec.Error(ctx, err)
525 | return graphql.Null
526 | }
527 | rctx := &graphql.ResolverContext{
528 | Object: "Mutation",
529 | Args: args,
530 | Field: field,
531 | }
532 | ctx = graphql.WithResolverContext(ctx, rctx)
533 | resTmp := ec.FieldMiddleware(ctx, nil, func(ctx context.Context) (interface{}, error) {
534 | return ec.resolvers.Mutation().DeleteChannel(ctx, args["ID"].(int))
535 | })
536 | if resTmp == nil {
537 | if !ec.HasError(rctx) {
538 | ec.Errorf(ctx, "must not be null")
539 | }
540 | return graphql.Null
541 | }
542 | res := resTmp.(model.Channel)
543 | rctx.Result = res
544 |
545 | return ec._Channel(ctx, field.Selections, &res)
546 | }
547 |
548 | var queryImplementors = []string{"Query"}
549 |
550 | // nolint: gocyclo, errcheck, gas, goconst
551 | func (ec *executionContext) _Query(ctx context.Context, sel ast.SelectionSet) graphql.Marshaler {
552 | fields := graphql.CollectFields(ctx, sel, queryImplementors)
553 |
554 | ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
555 | Object: "Query",
556 | })
557 |
558 | var wg sync.WaitGroup
559 | out := graphql.NewOrderedMap(len(fields))
560 | invalid := false
561 | for i, field := range fields {
562 | out.Keys[i] = field.Alias
563 |
564 | switch field.Name {
565 | case "__typename":
566 | out.Values[i] = graphql.MarshalString("Query")
567 | case "channels":
568 | wg.Add(1)
569 | go func(i int, field graphql.CollectedField) {
570 | out.Values[i] = ec._Query_channels(ctx, field)
571 | if out.Values[i] == graphql.Null {
572 | invalid = true
573 | }
574 | wg.Done()
575 | }(i, field)
576 | case "__type":
577 | out.Values[i] = ec._Query___type(ctx, field)
578 | case "__schema":
579 | out.Values[i] = ec._Query___schema(ctx, field)
580 | default:
581 | panic("unknown field " + strconv.Quote(field.Name))
582 | }
583 | }
584 | wg.Wait()
585 | if invalid {
586 | return graphql.Null
587 | }
588 | return out
589 | }
590 |
591 | // nolint: vetshadow
592 | func (ec *executionContext) _Query_channels(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
593 | rctx := &graphql.ResolverContext{
594 | Object: "Query",
595 | Args: nil,
596 | Field: field,
597 | }
598 | ctx = graphql.WithResolverContext(ctx, rctx)
599 | resTmp := ec.FieldMiddleware(ctx, nil, func(ctx context.Context) (interface{}, error) {
600 | return ec.resolvers.Query().Channels(ctx)
601 | })
602 | if resTmp == nil {
603 | if !ec.HasError(rctx) {
604 | ec.Errorf(ctx, "must not be null")
605 | }
606 | return graphql.Null
607 | }
608 | res := resTmp.([]model.Channel)
609 | rctx.Result = res
610 |
611 | arr1 := make(graphql.Array, len(res))
612 | var wg sync.WaitGroup
613 |
614 | isLen1 := len(res) == 1
615 | if !isLen1 {
616 | wg.Add(len(res))
617 | }
618 |
619 | for idx1 := range res {
620 | idx1 := idx1
621 | rctx := &graphql.ResolverContext{
622 | Index: &idx1,
623 | Result: &res[idx1],
624 | }
625 | ctx := graphql.WithResolverContext(ctx, rctx)
626 | f := func(idx1 int) {
627 | if !isLen1 {
628 | defer wg.Done()
629 | }
630 | arr1[idx1] = func() graphql.Marshaler {
631 |
632 | return ec._Channel(ctx, field.Selections, &res[idx1])
633 | }()
634 | }
635 | if isLen1 {
636 | f(idx1)
637 | } else {
638 | go f(idx1)
639 | }
640 |
641 | }
642 | wg.Wait()
643 | return arr1
644 | }
645 |
646 | // nolint: vetshadow
647 | func (ec *executionContext) _Query___type(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
648 | rawArgs := field.ArgumentMap(ec.Variables)
649 | args, err := field_Query___type_args(rawArgs)
650 | if err != nil {
651 | ec.Error(ctx, err)
652 | return graphql.Null
653 | }
654 | rctx := &graphql.ResolverContext{
655 | Object: "Query",
656 | Args: args,
657 | Field: field,
658 | }
659 | ctx = graphql.WithResolverContext(ctx, rctx)
660 | resTmp := ec.FieldMiddleware(ctx, nil, func(ctx context.Context) (interface{}, error) {
661 | return ec.introspectType(args["name"].(string)), nil
662 | })
663 | if resTmp == nil {
664 | return graphql.Null
665 | }
666 | res := resTmp.(*introspection.Type)
667 | rctx.Result = res
668 |
669 | if res == nil {
670 | return graphql.Null
671 | }
672 |
673 | return ec.___Type(ctx, field.Selections, res)
674 | }
675 |
676 | // nolint: vetshadow
677 | func (ec *executionContext) _Query___schema(ctx context.Context, field graphql.CollectedField) graphql.Marshaler {
678 | rctx := &graphql.ResolverContext{
679 | Object: "Query",
680 | Args: nil,
681 | Field: field,
682 | }
683 | ctx = graphql.WithResolverContext(ctx, rctx)
684 | resTmp := ec.FieldMiddleware(ctx, nil, func(ctx context.Context) (interface{}, error) {
685 | return ec.introspectSchema(), nil
686 | })
687 | if resTmp == nil {
688 | return graphql.Null
689 | }
690 | res := resTmp.(*introspection.Schema)
691 | rctx.Result = res
692 |
693 | if res == nil {
694 | return graphql.Null
695 | }
696 |
697 | return ec.___Schema(ctx, field.Selections, res)
698 | }
699 |
700 | var subscriptionImplementors = []string{"Subscription"}
701 |
702 | // nolint: gocyclo, errcheck, gas, goconst
703 | func (ec *executionContext) _Subscription(ctx context.Context, sel ast.SelectionSet) func() graphql.Marshaler {
704 | fields := graphql.CollectFields(ctx, sel, subscriptionImplementors)
705 | ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
706 | Object: "Subscription",
707 | })
708 | if len(fields) != 1 {
709 | ec.Errorf(ctx, "must subscribe to exactly one stream")
710 | return nil
711 | }
712 |
713 | switch fields[0].Name {
714 | case "subscriptionChannelAdded":
715 | return ec._Subscription_subscriptionChannelAdded(ctx, fields[0])
716 | case "subscriptionChannelDeleted":
717 | return ec._Subscription_subscriptionChannelDeleted(ctx, fields[0])
718 | case "subscriptionChannelUpdated":
719 | return ec._Subscription_subscriptionChannelUpdated(ctx, fields[0])
720 | default:
721 | panic("unknown field " + strconv.Quote(fields[0].Name))
722 | }
723 | }
724 |
725 | func (ec *executionContext) _Subscription_subscriptionChannelAdded(ctx context.Context, field graphql.CollectedField) func() graphql.Marshaler {
726 | ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
727 | Field: field,
728 | })
729 | results, err := ec.resolvers.Subscription().SubscriptionChannelAdded(ctx)
730 | if err != nil {
731 | ec.Error(ctx, err)
732 | return nil
733 | }
734 | return func() graphql.Marshaler {
735 | res, ok := <-results
736 | if !ok {
737 | return nil
738 | }
739 | var out graphql.OrderedMap
740 | out.Add(field.Alias, func() graphql.Marshaler {
741 | return ec._Channel(ctx, field.Selections, &res)
742 | }())
743 | return &out
744 | }
745 | }
746 |
747 | func (ec *executionContext) _Subscription_subscriptionChannelDeleted(ctx context.Context, field graphql.CollectedField) func() graphql.Marshaler {
748 | ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
749 | Field: field,
750 | })
751 | results, err := ec.resolvers.Subscription().SubscriptionChannelDeleted(ctx)
752 | if err != nil {
753 | ec.Error(ctx, err)
754 | return nil
755 | }
756 | return func() graphql.Marshaler {
757 | res, ok := <-results
758 | if !ok {
759 | return nil
760 | }
761 | var out graphql.OrderedMap
762 | out.Add(field.Alias, func() graphql.Marshaler {
763 | return ec._Channel(ctx, field.Selections, &res)
764 | }())
765 | return &out
766 | }
767 | }
768 |
769 | func (ec *executionContext) _Subscription_subscriptionChannelUpdated(ctx context.Context, field graphql.CollectedField) func() graphql.Marshaler {
770 | ctx = graphql.WithResolverContext(ctx, &graphql.ResolverContext{
771 | Field: field,
772 | })
773 | results, err := ec.resolvers.Subscription().SubscriptionChannelUpdated(ctx)
774 | if err != nil {
775 | ec.Error(ctx, err)
776 | return nil
777 | }
778 | return func() graphql.Marshaler {
779 | res, ok := <-results
780 | if !ok {
781 | return nil
782 | }
783 | var out graphql.OrderedMap
784 | out.Add(field.Alias, func() graphql.Marshaler {
785 | return ec._Channel(ctx, field.Selections, &res)
786 | }())
787 | return &out
788 | }
789 | }
790 |
791 | var __DirectiveImplementors = []string{"__Directive"}
792 |
793 | // nolint: gocyclo, errcheck, gas, goconst
794 | func (ec *executionContext) ___Directive(ctx context.Context, sel ast.SelectionSet, obj *introspection.Directive) graphql.Marshaler {
795 | fields := graphql.CollectFields(ctx, sel, __DirectiveImplementors)
796 |
797 | out := graphql.NewOrderedMap(len(fields))
798 | invalid := false
799 | for i, field := range fields {
800 | out.Keys[i] = field.Alias
801 |
802 | switch field.Name {
803 | case "__typename":
804 | out.Values[i] = graphql.MarshalString("__Directive")
805 | case "name":
806 | out.Values[i] = ec.___Directive_name(ctx, field, obj)
807 | if out.Values[i] == graphql.Null {
808 | invalid = true
809 | }
810 | case "description":
811 | out.Values[i] = ec.___Directive_description(ctx, field, obj)
812 | case "locations":
813 | out.Values[i] = ec.___Directive_locations(ctx, field, obj)
814 | if out.Values[i] == graphql.Null {
815 | invalid = true
816 | }
817 | case "args":
818 | out.Values[i] = ec.___Directive_args(ctx, field, obj)
819 | if out.Values[i] == graphql.Null {
820 | invalid = true
821 | }
822 | default:
823 | panic("unknown field " + strconv.Quote(field.Name))
824 | }
825 | }
826 |
827 | if invalid {
828 | return graphql.Null
829 | }
830 | return out
831 | }
832 |
833 | // nolint: vetshadow
834 | func (ec *executionContext) ___Directive_name(ctx context.Context, field graphql.CollectedField, obj *introspection.Directive) graphql.Marshaler {
835 | rctx := &graphql.ResolverContext{
836 | Object: "__Directive",
837 | Args: nil,
838 | Field: field,
839 | }
840 | ctx = graphql.WithResolverContext(ctx, rctx)
841 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
842 | return obj.Name, nil
843 | })
844 | if resTmp == nil {
845 | if !ec.HasError(rctx) {
846 | ec.Errorf(ctx, "must not be null")
847 | }
848 | return graphql.Null
849 | }
850 | res := resTmp.(string)
851 | rctx.Result = res
852 | return graphql.MarshalString(res)
853 | }
854 |
855 | // nolint: vetshadow
856 | func (ec *executionContext) ___Directive_description(ctx context.Context, field graphql.CollectedField, obj *introspection.Directive) graphql.Marshaler {
857 | rctx := &graphql.ResolverContext{
858 | Object: "__Directive",
859 | Args: nil,
860 | Field: field,
861 | }
862 | ctx = graphql.WithResolverContext(ctx, rctx)
863 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
864 | return obj.Description, nil
865 | })
866 | if resTmp == nil {
867 | return graphql.Null
868 | }
869 | res := resTmp.(string)
870 | rctx.Result = res
871 | return graphql.MarshalString(res)
872 | }
873 |
874 | // nolint: vetshadow
875 | func (ec *executionContext) ___Directive_locations(ctx context.Context, field graphql.CollectedField, obj *introspection.Directive) graphql.Marshaler {
876 | rctx := &graphql.ResolverContext{
877 | Object: "__Directive",
878 | Args: nil,
879 | Field: field,
880 | }
881 | ctx = graphql.WithResolverContext(ctx, rctx)
882 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
883 | return obj.Locations, nil
884 | })
885 | if resTmp == nil {
886 | if !ec.HasError(rctx) {
887 | ec.Errorf(ctx, "must not be null")
888 | }
889 | return graphql.Null
890 | }
891 | res := resTmp.([]string)
892 | rctx.Result = res
893 |
894 | arr1 := make(graphql.Array, len(res))
895 |
896 | for idx1 := range res {
897 | arr1[idx1] = func() graphql.Marshaler {
898 | return graphql.MarshalString(res[idx1])
899 | }()
900 | }
901 |
902 | return arr1
903 | }
904 |
905 | // nolint: vetshadow
906 | func (ec *executionContext) ___Directive_args(ctx context.Context, field graphql.CollectedField, obj *introspection.Directive) graphql.Marshaler {
907 | rctx := &graphql.ResolverContext{
908 | Object: "__Directive",
909 | Args: nil,
910 | Field: field,
911 | }
912 | ctx = graphql.WithResolverContext(ctx, rctx)
913 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
914 | return obj.Args, nil
915 | })
916 | if resTmp == nil {
917 | if !ec.HasError(rctx) {
918 | ec.Errorf(ctx, "must not be null")
919 | }
920 | return graphql.Null
921 | }
922 | res := resTmp.([]introspection.InputValue)
923 | rctx.Result = res
924 |
925 | arr1 := make(graphql.Array, len(res))
926 | var wg sync.WaitGroup
927 |
928 | isLen1 := len(res) == 1
929 | if !isLen1 {
930 | wg.Add(len(res))
931 | }
932 |
933 | for idx1 := range res {
934 | idx1 := idx1
935 | rctx := &graphql.ResolverContext{
936 | Index: &idx1,
937 | Result: &res[idx1],
938 | }
939 | ctx := graphql.WithResolverContext(ctx, rctx)
940 | f := func(idx1 int) {
941 | if !isLen1 {
942 | defer wg.Done()
943 | }
944 | arr1[idx1] = func() graphql.Marshaler {
945 |
946 | return ec.___InputValue(ctx, field.Selections, &res[idx1])
947 | }()
948 | }
949 | if isLen1 {
950 | f(idx1)
951 | } else {
952 | go f(idx1)
953 | }
954 |
955 | }
956 | wg.Wait()
957 | return arr1
958 | }
959 |
960 | var __EnumValueImplementors = []string{"__EnumValue"}
961 |
962 | // nolint: gocyclo, errcheck, gas, goconst
963 | func (ec *executionContext) ___EnumValue(ctx context.Context, sel ast.SelectionSet, obj *introspection.EnumValue) graphql.Marshaler {
964 | fields := graphql.CollectFields(ctx, sel, __EnumValueImplementors)
965 |
966 | out := graphql.NewOrderedMap(len(fields))
967 | invalid := false
968 | for i, field := range fields {
969 | out.Keys[i] = field.Alias
970 |
971 | switch field.Name {
972 | case "__typename":
973 | out.Values[i] = graphql.MarshalString("__EnumValue")
974 | case "name":
975 | out.Values[i] = ec.___EnumValue_name(ctx, field, obj)
976 | if out.Values[i] == graphql.Null {
977 | invalid = true
978 | }
979 | case "description":
980 | out.Values[i] = ec.___EnumValue_description(ctx, field, obj)
981 | case "isDeprecated":
982 | out.Values[i] = ec.___EnumValue_isDeprecated(ctx, field, obj)
983 | if out.Values[i] == graphql.Null {
984 | invalid = true
985 | }
986 | case "deprecationReason":
987 | out.Values[i] = ec.___EnumValue_deprecationReason(ctx, field, obj)
988 | default:
989 | panic("unknown field " + strconv.Quote(field.Name))
990 | }
991 | }
992 |
993 | if invalid {
994 | return graphql.Null
995 | }
996 | return out
997 | }
998 |
999 | // nolint: vetshadow
1000 | func (ec *executionContext) ___EnumValue_name(ctx context.Context, field graphql.CollectedField, obj *introspection.EnumValue) graphql.Marshaler {
1001 | rctx := &graphql.ResolverContext{
1002 | Object: "__EnumValue",
1003 | Args: nil,
1004 | Field: field,
1005 | }
1006 | ctx = graphql.WithResolverContext(ctx, rctx)
1007 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1008 | return obj.Name, nil
1009 | })
1010 | if resTmp == nil {
1011 | if !ec.HasError(rctx) {
1012 | ec.Errorf(ctx, "must not be null")
1013 | }
1014 | return graphql.Null
1015 | }
1016 | res := resTmp.(string)
1017 | rctx.Result = res
1018 | return graphql.MarshalString(res)
1019 | }
1020 |
1021 | // nolint: vetshadow
1022 | func (ec *executionContext) ___EnumValue_description(ctx context.Context, field graphql.CollectedField, obj *introspection.EnumValue) graphql.Marshaler {
1023 | rctx := &graphql.ResolverContext{
1024 | Object: "__EnumValue",
1025 | Args: nil,
1026 | Field: field,
1027 | }
1028 | ctx = graphql.WithResolverContext(ctx, rctx)
1029 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1030 | return obj.Description, nil
1031 | })
1032 | if resTmp == nil {
1033 | return graphql.Null
1034 | }
1035 | res := resTmp.(string)
1036 | rctx.Result = res
1037 | return graphql.MarshalString(res)
1038 | }
1039 |
1040 | // nolint: vetshadow
1041 | func (ec *executionContext) ___EnumValue_isDeprecated(ctx context.Context, field graphql.CollectedField, obj *introspection.EnumValue) graphql.Marshaler {
1042 | rctx := &graphql.ResolverContext{
1043 | Object: "__EnumValue",
1044 | Args: nil,
1045 | Field: field,
1046 | }
1047 | ctx = graphql.WithResolverContext(ctx, rctx)
1048 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1049 | return obj.IsDeprecated, nil
1050 | })
1051 | if resTmp == nil {
1052 | if !ec.HasError(rctx) {
1053 | ec.Errorf(ctx, "must not be null")
1054 | }
1055 | return graphql.Null
1056 | }
1057 | res := resTmp.(bool)
1058 | rctx.Result = res
1059 | return graphql.MarshalBoolean(res)
1060 | }
1061 |
1062 | // nolint: vetshadow
1063 | func (ec *executionContext) ___EnumValue_deprecationReason(ctx context.Context, field graphql.CollectedField, obj *introspection.EnumValue) graphql.Marshaler {
1064 | rctx := &graphql.ResolverContext{
1065 | Object: "__EnumValue",
1066 | Args: nil,
1067 | Field: field,
1068 | }
1069 | ctx = graphql.WithResolverContext(ctx, rctx)
1070 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1071 | return obj.DeprecationReason, nil
1072 | })
1073 | if resTmp == nil {
1074 | return graphql.Null
1075 | }
1076 | res := resTmp.(string)
1077 | rctx.Result = res
1078 | return graphql.MarshalString(res)
1079 | }
1080 |
1081 | var __FieldImplementors = []string{"__Field"}
1082 |
1083 | // nolint: gocyclo, errcheck, gas, goconst
1084 | func (ec *executionContext) ___Field(ctx context.Context, sel ast.SelectionSet, obj *introspection.Field) graphql.Marshaler {
1085 | fields := graphql.CollectFields(ctx, sel, __FieldImplementors)
1086 |
1087 | out := graphql.NewOrderedMap(len(fields))
1088 | invalid := false
1089 | for i, field := range fields {
1090 | out.Keys[i] = field.Alias
1091 |
1092 | switch field.Name {
1093 | case "__typename":
1094 | out.Values[i] = graphql.MarshalString("__Field")
1095 | case "name":
1096 | out.Values[i] = ec.___Field_name(ctx, field, obj)
1097 | if out.Values[i] == graphql.Null {
1098 | invalid = true
1099 | }
1100 | case "description":
1101 | out.Values[i] = ec.___Field_description(ctx, field, obj)
1102 | case "args":
1103 | out.Values[i] = ec.___Field_args(ctx, field, obj)
1104 | if out.Values[i] == graphql.Null {
1105 | invalid = true
1106 | }
1107 | case "type":
1108 | out.Values[i] = ec.___Field_type(ctx, field, obj)
1109 | if out.Values[i] == graphql.Null {
1110 | invalid = true
1111 | }
1112 | case "isDeprecated":
1113 | out.Values[i] = ec.___Field_isDeprecated(ctx, field, obj)
1114 | if out.Values[i] == graphql.Null {
1115 | invalid = true
1116 | }
1117 | case "deprecationReason":
1118 | out.Values[i] = ec.___Field_deprecationReason(ctx, field, obj)
1119 | default:
1120 | panic("unknown field " + strconv.Quote(field.Name))
1121 | }
1122 | }
1123 |
1124 | if invalid {
1125 | return graphql.Null
1126 | }
1127 | return out
1128 | }
1129 |
1130 | // nolint: vetshadow
1131 | func (ec *executionContext) ___Field_name(ctx context.Context, field graphql.CollectedField, obj *introspection.Field) graphql.Marshaler {
1132 | rctx := &graphql.ResolverContext{
1133 | Object: "__Field",
1134 | Args: nil,
1135 | Field: field,
1136 | }
1137 | ctx = graphql.WithResolverContext(ctx, rctx)
1138 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1139 | return obj.Name, nil
1140 | })
1141 | if resTmp == nil {
1142 | if !ec.HasError(rctx) {
1143 | ec.Errorf(ctx, "must not be null")
1144 | }
1145 | return graphql.Null
1146 | }
1147 | res := resTmp.(string)
1148 | rctx.Result = res
1149 | return graphql.MarshalString(res)
1150 | }
1151 |
1152 | // nolint: vetshadow
1153 | func (ec *executionContext) ___Field_description(ctx context.Context, field graphql.CollectedField, obj *introspection.Field) graphql.Marshaler {
1154 | rctx := &graphql.ResolverContext{
1155 | Object: "__Field",
1156 | Args: nil,
1157 | Field: field,
1158 | }
1159 | ctx = graphql.WithResolverContext(ctx, rctx)
1160 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1161 | return obj.Description, nil
1162 | })
1163 | if resTmp == nil {
1164 | return graphql.Null
1165 | }
1166 | res := resTmp.(string)
1167 | rctx.Result = res
1168 | return graphql.MarshalString(res)
1169 | }
1170 |
1171 | // nolint: vetshadow
1172 | func (ec *executionContext) ___Field_args(ctx context.Context, field graphql.CollectedField, obj *introspection.Field) graphql.Marshaler {
1173 | rctx := &graphql.ResolverContext{
1174 | Object: "__Field",
1175 | Args: nil,
1176 | Field: field,
1177 | }
1178 | ctx = graphql.WithResolverContext(ctx, rctx)
1179 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1180 | return obj.Args, nil
1181 | })
1182 | if resTmp == nil {
1183 | if !ec.HasError(rctx) {
1184 | ec.Errorf(ctx, "must not be null")
1185 | }
1186 | return graphql.Null
1187 | }
1188 | res := resTmp.([]introspection.InputValue)
1189 | rctx.Result = res
1190 |
1191 | arr1 := make(graphql.Array, len(res))
1192 | var wg sync.WaitGroup
1193 |
1194 | isLen1 := len(res) == 1
1195 | if !isLen1 {
1196 | wg.Add(len(res))
1197 | }
1198 |
1199 | for idx1 := range res {
1200 | idx1 := idx1
1201 | rctx := &graphql.ResolverContext{
1202 | Index: &idx1,
1203 | Result: &res[idx1],
1204 | }
1205 | ctx := graphql.WithResolverContext(ctx, rctx)
1206 | f := func(idx1 int) {
1207 | if !isLen1 {
1208 | defer wg.Done()
1209 | }
1210 | arr1[idx1] = func() graphql.Marshaler {
1211 |
1212 | return ec.___InputValue(ctx, field.Selections, &res[idx1])
1213 | }()
1214 | }
1215 | if isLen1 {
1216 | f(idx1)
1217 | } else {
1218 | go f(idx1)
1219 | }
1220 |
1221 | }
1222 | wg.Wait()
1223 | return arr1
1224 | }
1225 |
1226 | // nolint: vetshadow
1227 | func (ec *executionContext) ___Field_type(ctx context.Context, field graphql.CollectedField, obj *introspection.Field) graphql.Marshaler {
1228 | rctx := &graphql.ResolverContext{
1229 | Object: "__Field",
1230 | Args: nil,
1231 | Field: field,
1232 | }
1233 | ctx = graphql.WithResolverContext(ctx, rctx)
1234 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1235 | return obj.Type, nil
1236 | })
1237 | if resTmp == nil {
1238 | if !ec.HasError(rctx) {
1239 | ec.Errorf(ctx, "must not be null")
1240 | }
1241 | return graphql.Null
1242 | }
1243 | res := resTmp.(*introspection.Type)
1244 | rctx.Result = res
1245 |
1246 | if res == nil {
1247 | if !ec.HasError(rctx) {
1248 | ec.Errorf(ctx, "must not be null")
1249 | }
1250 | return graphql.Null
1251 | }
1252 |
1253 | return ec.___Type(ctx, field.Selections, res)
1254 | }
1255 |
1256 | // nolint: vetshadow
1257 | func (ec *executionContext) ___Field_isDeprecated(ctx context.Context, field graphql.CollectedField, obj *introspection.Field) graphql.Marshaler {
1258 | rctx := &graphql.ResolverContext{
1259 | Object: "__Field",
1260 | Args: nil,
1261 | Field: field,
1262 | }
1263 | ctx = graphql.WithResolverContext(ctx, rctx)
1264 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1265 | return obj.IsDeprecated, nil
1266 | })
1267 | if resTmp == nil {
1268 | if !ec.HasError(rctx) {
1269 | ec.Errorf(ctx, "must not be null")
1270 | }
1271 | return graphql.Null
1272 | }
1273 | res := resTmp.(bool)
1274 | rctx.Result = res
1275 | return graphql.MarshalBoolean(res)
1276 | }
1277 |
1278 | // nolint: vetshadow
1279 | func (ec *executionContext) ___Field_deprecationReason(ctx context.Context, field graphql.CollectedField, obj *introspection.Field) graphql.Marshaler {
1280 | rctx := &graphql.ResolverContext{
1281 | Object: "__Field",
1282 | Args: nil,
1283 | Field: field,
1284 | }
1285 | ctx = graphql.WithResolverContext(ctx, rctx)
1286 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1287 | return obj.DeprecationReason, nil
1288 | })
1289 | if resTmp == nil {
1290 | return graphql.Null
1291 | }
1292 | res := resTmp.(string)
1293 | rctx.Result = res
1294 | return graphql.MarshalString(res)
1295 | }
1296 |
1297 | var __InputValueImplementors = []string{"__InputValue"}
1298 |
1299 | // nolint: gocyclo, errcheck, gas, goconst
1300 | func (ec *executionContext) ___InputValue(ctx context.Context, sel ast.SelectionSet, obj *introspection.InputValue) graphql.Marshaler {
1301 | fields := graphql.CollectFields(ctx, sel, __InputValueImplementors)
1302 |
1303 | out := graphql.NewOrderedMap(len(fields))
1304 | invalid := false
1305 | for i, field := range fields {
1306 | out.Keys[i] = field.Alias
1307 |
1308 | switch field.Name {
1309 | case "__typename":
1310 | out.Values[i] = graphql.MarshalString("__InputValue")
1311 | case "name":
1312 | out.Values[i] = ec.___InputValue_name(ctx, field, obj)
1313 | if out.Values[i] == graphql.Null {
1314 | invalid = true
1315 | }
1316 | case "description":
1317 | out.Values[i] = ec.___InputValue_description(ctx, field, obj)
1318 | case "type":
1319 | out.Values[i] = ec.___InputValue_type(ctx, field, obj)
1320 | if out.Values[i] == graphql.Null {
1321 | invalid = true
1322 | }
1323 | case "defaultValue":
1324 | out.Values[i] = ec.___InputValue_defaultValue(ctx, field, obj)
1325 | default:
1326 | panic("unknown field " + strconv.Quote(field.Name))
1327 | }
1328 | }
1329 |
1330 | if invalid {
1331 | return graphql.Null
1332 | }
1333 | return out
1334 | }
1335 |
1336 | // nolint: vetshadow
1337 | func (ec *executionContext) ___InputValue_name(ctx context.Context, field graphql.CollectedField, obj *introspection.InputValue) graphql.Marshaler {
1338 | rctx := &graphql.ResolverContext{
1339 | Object: "__InputValue",
1340 | Args: nil,
1341 | Field: field,
1342 | }
1343 | ctx = graphql.WithResolverContext(ctx, rctx)
1344 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1345 | return obj.Name, nil
1346 | })
1347 | if resTmp == nil {
1348 | if !ec.HasError(rctx) {
1349 | ec.Errorf(ctx, "must not be null")
1350 | }
1351 | return graphql.Null
1352 | }
1353 | res := resTmp.(string)
1354 | rctx.Result = res
1355 | return graphql.MarshalString(res)
1356 | }
1357 |
1358 | // nolint: vetshadow
1359 | func (ec *executionContext) ___InputValue_description(ctx context.Context, field graphql.CollectedField, obj *introspection.InputValue) graphql.Marshaler {
1360 | rctx := &graphql.ResolverContext{
1361 | Object: "__InputValue",
1362 | Args: nil,
1363 | Field: field,
1364 | }
1365 | ctx = graphql.WithResolverContext(ctx, rctx)
1366 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1367 | return obj.Description, nil
1368 | })
1369 | if resTmp == nil {
1370 | return graphql.Null
1371 | }
1372 | res := resTmp.(string)
1373 | rctx.Result = res
1374 | return graphql.MarshalString(res)
1375 | }
1376 |
1377 | // nolint: vetshadow
1378 | func (ec *executionContext) ___InputValue_type(ctx context.Context, field graphql.CollectedField, obj *introspection.InputValue) graphql.Marshaler {
1379 | rctx := &graphql.ResolverContext{
1380 | Object: "__InputValue",
1381 | Args: nil,
1382 | Field: field,
1383 | }
1384 | ctx = graphql.WithResolverContext(ctx, rctx)
1385 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1386 | return obj.Type, nil
1387 | })
1388 | if resTmp == nil {
1389 | if !ec.HasError(rctx) {
1390 | ec.Errorf(ctx, "must not be null")
1391 | }
1392 | return graphql.Null
1393 | }
1394 | res := resTmp.(*introspection.Type)
1395 | rctx.Result = res
1396 |
1397 | if res == nil {
1398 | if !ec.HasError(rctx) {
1399 | ec.Errorf(ctx, "must not be null")
1400 | }
1401 | return graphql.Null
1402 | }
1403 |
1404 | return ec.___Type(ctx, field.Selections, res)
1405 | }
1406 |
1407 | // nolint: vetshadow
1408 | func (ec *executionContext) ___InputValue_defaultValue(ctx context.Context, field graphql.CollectedField, obj *introspection.InputValue) graphql.Marshaler {
1409 | rctx := &graphql.ResolverContext{
1410 | Object: "__InputValue",
1411 | Args: nil,
1412 | Field: field,
1413 | }
1414 | ctx = graphql.WithResolverContext(ctx, rctx)
1415 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1416 | return obj.DefaultValue, nil
1417 | })
1418 | if resTmp == nil {
1419 | return graphql.Null
1420 | }
1421 | res := resTmp.(*string)
1422 | rctx.Result = res
1423 |
1424 | if res == nil {
1425 | return graphql.Null
1426 | }
1427 | return graphql.MarshalString(*res)
1428 | }
1429 |
1430 | var __SchemaImplementors = []string{"__Schema"}
1431 |
1432 | // nolint: gocyclo, errcheck, gas, goconst
1433 | func (ec *executionContext) ___Schema(ctx context.Context, sel ast.SelectionSet, obj *introspection.Schema) graphql.Marshaler {
1434 | fields := graphql.CollectFields(ctx, sel, __SchemaImplementors)
1435 |
1436 | out := graphql.NewOrderedMap(len(fields))
1437 | invalid := false
1438 | for i, field := range fields {
1439 | out.Keys[i] = field.Alias
1440 |
1441 | switch field.Name {
1442 | case "__typename":
1443 | out.Values[i] = graphql.MarshalString("__Schema")
1444 | case "types":
1445 | out.Values[i] = ec.___Schema_types(ctx, field, obj)
1446 | if out.Values[i] == graphql.Null {
1447 | invalid = true
1448 | }
1449 | case "queryType":
1450 | out.Values[i] = ec.___Schema_queryType(ctx, field, obj)
1451 | if out.Values[i] == graphql.Null {
1452 | invalid = true
1453 | }
1454 | case "mutationType":
1455 | out.Values[i] = ec.___Schema_mutationType(ctx, field, obj)
1456 | case "subscriptionType":
1457 | out.Values[i] = ec.___Schema_subscriptionType(ctx, field, obj)
1458 | case "directives":
1459 | out.Values[i] = ec.___Schema_directives(ctx, field, obj)
1460 | if out.Values[i] == graphql.Null {
1461 | invalid = true
1462 | }
1463 | default:
1464 | panic("unknown field " + strconv.Quote(field.Name))
1465 | }
1466 | }
1467 |
1468 | if invalid {
1469 | return graphql.Null
1470 | }
1471 | return out
1472 | }
1473 |
1474 | // nolint: vetshadow
1475 | func (ec *executionContext) ___Schema_types(ctx context.Context, field graphql.CollectedField, obj *introspection.Schema) graphql.Marshaler {
1476 | rctx := &graphql.ResolverContext{
1477 | Object: "__Schema",
1478 | Args: nil,
1479 | Field: field,
1480 | }
1481 | ctx = graphql.WithResolverContext(ctx, rctx)
1482 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1483 | return obj.Types(), nil
1484 | })
1485 | if resTmp == nil {
1486 | if !ec.HasError(rctx) {
1487 | ec.Errorf(ctx, "must not be null")
1488 | }
1489 | return graphql.Null
1490 | }
1491 | res := resTmp.([]introspection.Type)
1492 | rctx.Result = res
1493 |
1494 | arr1 := make(graphql.Array, len(res))
1495 | var wg sync.WaitGroup
1496 |
1497 | isLen1 := len(res) == 1
1498 | if !isLen1 {
1499 | wg.Add(len(res))
1500 | }
1501 |
1502 | for idx1 := range res {
1503 | idx1 := idx1
1504 | rctx := &graphql.ResolverContext{
1505 | Index: &idx1,
1506 | Result: &res[idx1],
1507 | }
1508 | ctx := graphql.WithResolverContext(ctx, rctx)
1509 | f := func(idx1 int) {
1510 | if !isLen1 {
1511 | defer wg.Done()
1512 | }
1513 | arr1[idx1] = func() graphql.Marshaler {
1514 |
1515 | return ec.___Type(ctx, field.Selections, &res[idx1])
1516 | }()
1517 | }
1518 | if isLen1 {
1519 | f(idx1)
1520 | } else {
1521 | go f(idx1)
1522 | }
1523 |
1524 | }
1525 | wg.Wait()
1526 | return arr1
1527 | }
1528 |
1529 | // nolint: vetshadow
1530 | func (ec *executionContext) ___Schema_queryType(ctx context.Context, field graphql.CollectedField, obj *introspection.Schema) graphql.Marshaler {
1531 | rctx := &graphql.ResolverContext{
1532 | Object: "__Schema",
1533 | Args: nil,
1534 | Field: field,
1535 | }
1536 | ctx = graphql.WithResolverContext(ctx, rctx)
1537 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1538 | return obj.QueryType(), nil
1539 | })
1540 | if resTmp == nil {
1541 | if !ec.HasError(rctx) {
1542 | ec.Errorf(ctx, "must not be null")
1543 | }
1544 | return graphql.Null
1545 | }
1546 | res := resTmp.(*introspection.Type)
1547 | rctx.Result = res
1548 |
1549 | if res == nil {
1550 | if !ec.HasError(rctx) {
1551 | ec.Errorf(ctx, "must not be null")
1552 | }
1553 | return graphql.Null
1554 | }
1555 |
1556 | return ec.___Type(ctx, field.Selections, res)
1557 | }
1558 |
1559 | // nolint: vetshadow
1560 | func (ec *executionContext) ___Schema_mutationType(ctx context.Context, field graphql.CollectedField, obj *introspection.Schema) graphql.Marshaler {
1561 | rctx := &graphql.ResolverContext{
1562 | Object: "__Schema",
1563 | Args: nil,
1564 | Field: field,
1565 | }
1566 | ctx = graphql.WithResolverContext(ctx, rctx)
1567 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1568 | return obj.MutationType(), nil
1569 | })
1570 | if resTmp == nil {
1571 | return graphql.Null
1572 | }
1573 | res := resTmp.(*introspection.Type)
1574 | rctx.Result = res
1575 |
1576 | if res == nil {
1577 | return graphql.Null
1578 | }
1579 |
1580 | return ec.___Type(ctx, field.Selections, res)
1581 | }
1582 |
1583 | // nolint: vetshadow
1584 | func (ec *executionContext) ___Schema_subscriptionType(ctx context.Context, field graphql.CollectedField, obj *introspection.Schema) graphql.Marshaler {
1585 | rctx := &graphql.ResolverContext{
1586 | Object: "__Schema",
1587 | Args: nil,
1588 | Field: field,
1589 | }
1590 | ctx = graphql.WithResolverContext(ctx, rctx)
1591 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1592 | return obj.SubscriptionType(), nil
1593 | })
1594 | if resTmp == nil {
1595 | return graphql.Null
1596 | }
1597 | res := resTmp.(*introspection.Type)
1598 | rctx.Result = res
1599 |
1600 | if res == nil {
1601 | return graphql.Null
1602 | }
1603 |
1604 | return ec.___Type(ctx, field.Selections, res)
1605 | }
1606 |
1607 | // nolint: vetshadow
1608 | func (ec *executionContext) ___Schema_directives(ctx context.Context, field graphql.CollectedField, obj *introspection.Schema) graphql.Marshaler {
1609 | rctx := &graphql.ResolverContext{
1610 | Object: "__Schema",
1611 | Args: nil,
1612 | Field: field,
1613 | }
1614 | ctx = graphql.WithResolverContext(ctx, rctx)
1615 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1616 | return obj.Directives(), nil
1617 | })
1618 | if resTmp == nil {
1619 | if !ec.HasError(rctx) {
1620 | ec.Errorf(ctx, "must not be null")
1621 | }
1622 | return graphql.Null
1623 | }
1624 | res := resTmp.([]introspection.Directive)
1625 | rctx.Result = res
1626 |
1627 | arr1 := make(graphql.Array, len(res))
1628 | var wg sync.WaitGroup
1629 |
1630 | isLen1 := len(res) == 1
1631 | if !isLen1 {
1632 | wg.Add(len(res))
1633 | }
1634 |
1635 | for idx1 := range res {
1636 | idx1 := idx1
1637 | rctx := &graphql.ResolverContext{
1638 | Index: &idx1,
1639 | Result: &res[idx1],
1640 | }
1641 | ctx := graphql.WithResolverContext(ctx, rctx)
1642 | f := func(idx1 int) {
1643 | if !isLen1 {
1644 | defer wg.Done()
1645 | }
1646 | arr1[idx1] = func() graphql.Marshaler {
1647 |
1648 | return ec.___Directive(ctx, field.Selections, &res[idx1])
1649 | }()
1650 | }
1651 | if isLen1 {
1652 | f(idx1)
1653 | } else {
1654 | go f(idx1)
1655 | }
1656 |
1657 | }
1658 | wg.Wait()
1659 | return arr1
1660 | }
1661 |
1662 | var __TypeImplementors = []string{"__Type"}
1663 |
1664 | // nolint: gocyclo, errcheck, gas, goconst
1665 | func (ec *executionContext) ___Type(ctx context.Context, sel ast.SelectionSet, obj *introspection.Type) graphql.Marshaler {
1666 | fields := graphql.CollectFields(ctx, sel, __TypeImplementors)
1667 |
1668 | out := graphql.NewOrderedMap(len(fields))
1669 | invalid := false
1670 | for i, field := range fields {
1671 | out.Keys[i] = field.Alias
1672 |
1673 | switch field.Name {
1674 | case "__typename":
1675 | out.Values[i] = graphql.MarshalString("__Type")
1676 | case "kind":
1677 | out.Values[i] = ec.___Type_kind(ctx, field, obj)
1678 | if out.Values[i] == graphql.Null {
1679 | invalid = true
1680 | }
1681 | case "name":
1682 | out.Values[i] = ec.___Type_name(ctx, field, obj)
1683 | case "description":
1684 | out.Values[i] = ec.___Type_description(ctx, field, obj)
1685 | case "fields":
1686 | out.Values[i] = ec.___Type_fields(ctx, field, obj)
1687 | case "interfaces":
1688 | out.Values[i] = ec.___Type_interfaces(ctx, field, obj)
1689 | case "possibleTypes":
1690 | out.Values[i] = ec.___Type_possibleTypes(ctx, field, obj)
1691 | case "enumValues":
1692 | out.Values[i] = ec.___Type_enumValues(ctx, field, obj)
1693 | case "inputFields":
1694 | out.Values[i] = ec.___Type_inputFields(ctx, field, obj)
1695 | case "ofType":
1696 | out.Values[i] = ec.___Type_ofType(ctx, field, obj)
1697 | default:
1698 | panic("unknown field " + strconv.Quote(field.Name))
1699 | }
1700 | }
1701 |
1702 | if invalid {
1703 | return graphql.Null
1704 | }
1705 | return out
1706 | }
1707 |
1708 | // nolint: vetshadow
1709 | func (ec *executionContext) ___Type_kind(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1710 | rctx := &graphql.ResolverContext{
1711 | Object: "__Type",
1712 | Args: nil,
1713 | Field: field,
1714 | }
1715 | ctx = graphql.WithResolverContext(ctx, rctx)
1716 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1717 | return obj.Kind(), nil
1718 | })
1719 | if resTmp == nil {
1720 | if !ec.HasError(rctx) {
1721 | ec.Errorf(ctx, "must not be null")
1722 | }
1723 | return graphql.Null
1724 | }
1725 | res := resTmp.(string)
1726 | rctx.Result = res
1727 | return graphql.MarshalString(res)
1728 | }
1729 |
1730 | // nolint: vetshadow
1731 | func (ec *executionContext) ___Type_name(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1732 | rctx := &graphql.ResolverContext{
1733 | Object: "__Type",
1734 | Args: nil,
1735 | Field: field,
1736 | }
1737 | ctx = graphql.WithResolverContext(ctx, rctx)
1738 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1739 | return obj.Name(), nil
1740 | })
1741 | if resTmp == nil {
1742 | return graphql.Null
1743 | }
1744 | res := resTmp.(*string)
1745 | rctx.Result = res
1746 |
1747 | if res == nil {
1748 | return graphql.Null
1749 | }
1750 | return graphql.MarshalString(*res)
1751 | }
1752 |
1753 | // nolint: vetshadow
1754 | func (ec *executionContext) ___Type_description(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1755 | rctx := &graphql.ResolverContext{
1756 | Object: "__Type",
1757 | Args: nil,
1758 | Field: field,
1759 | }
1760 | ctx = graphql.WithResolverContext(ctx, rctx)
1761 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1762 | return obj.Description(), nil
1763 | })
1764 | if resTmp == nil {
1765 | return graphql.Null
1766 | }
1767 | res := resTmp.(string)
1768 | rctx.Result = res
1769 | return graphql.MarshalString(res)
1770 | }
1771 |
1772 | // nolint: vetshadow
1773 | func (ec *executionContext) ___Type_fields(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1774 | rawArgs := field.ArgumentMap(ec.Variables)
1775 | args, err := field___Type_fields_args(rawArgs)
1776 | if err != nil {
1777 | ec.Error(ctx, err)
1778 | return graphql.Null
1779 | }
1780 | rctx := &graphql.ResolverContext{
1781 | Object: "__Type",
1782 | Args: args,
1783 | Field: field,
1784 | }
1785 | ctx = graphql.WithResolverContext(ctx, rctx)
1786 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1787 | return obj.Fields(args["includeDeprecated"].(bool)), nil
1788 | })
1789 | if resTmp == nil {
1790 | return graphql.Null
1791 | }
1792 | res := resTmp.([]introspection.Field)
1793 | rctx.Result = res
1794 |
1795 | arr1 := make(graphql.Array, len(res))
1796 | var wg sync.WaitGroup
1797 |
1798 | isLen1 := len(res) == 1
1799 | if !isLen1 {
1800 | wg.Add(len(res))
1801 | }
1802 |
1803 | for idx1 := range res {
1804 | idx1 := idx1
1805 | rctx := &graphql.ResolverContext{
1806 | Index: &idx1,
1807 | Result: &res[idx1],
1808 | }
1809 | ctx := graphql.WithResolverContext(ctx, rctx)
1810 | f := func(idx1 int) {
1811 | if !isLen1 {
1812 | defer wg.Done()
1813 | }
1814 | arr1[idx1] = func() graphql.Marshaler {
1815 |
1816 | return ec.___Field(ctx, field.Selections, &res[idx1])
1817 | }()
1818 | }
1819 | if isLen1 {
1820 | f(idx1)
1821 | } else {
1822 | go f(idx1)
1823 | }
1824 |
1825 | }
1826 | wg.Wait()
1827 | return arr1
1828 | }
1829 |
1830 | // nolint: vetshadow
1831 | func (ec *executionContext) ___Type_interfaces(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1832 | rctx := &graphql.ResolverContext{
1833 | Object: "__Type",
1834 | Args: nil,
1835 | Field: field,
1836 | }
1837 | ctx = graphql.WithResolverContext(ctx, rctx)
1838 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1839 | return obj.Interfaces(), nil
1840 | })
1841 | if resTmp == nil {
1842 | return graphql.Null
1843 | }
1844 | res := resTmp.([]introspection.Type)
1845 | rctx.Result = res
1846 |
1847 | arr1 := make(graphql.Array, len(res))
1848 | var wg sync.WaitGroup
1849 |
1850 | isLen1 := len(res) == 1
1851 | if !isLen1 {
1852 | wg.Add(len(res))
1853 | }
1854 |
1855 | for idx1 := range res {
1856 | idx1 := idx1
1857 | rctx := &graphql.ResolverContext{
1858 | Index: &idx1,
1859 | Result: &res[idx1],
1860 | }
1861 | ctx := graphql.WithResolverContext(ctx, rctx)
1862 | f := func(idx1 int) {
1863 | if !isLen1 {
1864 | defer wg.Done()
1865 | }
1866 | arr1[idx1] = func() graphql.Marshaler {
1867 |
1868 | return ec.___Type(ctx, field.Selections, &res[idx1])
1869 | }()
1870 | }
1871 | if isLen1 {
1872 | f(idx1)
1873 | } else {
1874 | go f(idx1)
1875 | }
1876 |
1877 | }
1878 | wg.Wait()
1879 | return arr1
1880 | }
1881 |
1882 | // nolint: vetshadow
1883 | func (ec *executionContext) ___Type_possibleTypes(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1884 | rctx := &graphql.ResolverContext{
1885 | Object: "__Type",
1886 | Args: nil,
1887 | Field: field,
1888 | }
1889 | ctx = graphql.WithResolverContext(ctx, rctx)
1890 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1891 | return obj.PossibleTypes(), nil
1892 | })
1893 | if resTmp == nil {
1894 | return graphql.Null
1895 | }
1896 | res := resTmp.([]introspection.Type)
1897 | rctx.Result = res
1898 |
1899 | arr1 := make(graphql.Array, len(res))
1900 | var wg sync.WaitGroup
1901 |
1902 | isLen1 := len(res) == 1
1903 | if !isLen1 {
1904 | wg.Add(len(res))
1905 | }
1906 |
1907 | for idx1 := range res {
1908 | idx1 := idx1
1909 | rctx := &graphql.ResolverContext{
1910 | Index: &idx1,
1911 | Result: &res[idx1],
1912 | }
1913 | ctx := graphql.WithResolverContext(ctx, rctx)
1914 | f := func(idx1 int) {
1915 | if !isLen1 {
1916 | defer wg.Done()
1917 | }
1918 | arr1[idx1] = func() graphql.Marshaler {
1919 |
1920 | return ec.___Type(ctx, field.Selections, &res[idx1])
1921 | }()
1922 | }
1923 | if isLen1 {
1924 | f(idx1)
1925 | } else {
1926 | go f(idx1)
1927 | }
1928 |
1929 | }
1930 | wg.Wait()
1931 | return arr1
1932 | }
1933 |
1934 | // nolint: vetshadow
1935 | func (ec *executionContext) ___Type_enumValues(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1936 | rawArgs := field.ArgumentMap(ec.Variables)
1937 | args, err := field___Type_enumValues_args(rawArgs)
1938 | if err != nil {
1939 | ec.Error(ctx, err)
1940 | return graphql.Null
1941 | }
1942 | rctx := &graphql.ResolverContext{
1943 | Object: "__Type",
1944 | Args: args,
1945 | Field: field,
1946 | }
1947 | ctx = graphql.WithResolverContext(ctx, rctx)
1948 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
1949 | return obj.EnumValues(args["includeDeprecated"].(bool)), nil
1950 | })
1951 | if resTmp == nil {
1952 | return graphql.Null
1953 | }
1954 | res := resTmp.([]introspection.EnumValue)
1955 | rctx.Result = res
1956 |
1957 | arr1 := make(graphql.Array, len(res))
1958 | var wg sync.WaitGroup
1959 |
1960 | isLen1 := len(res) == 1
1961 | if !isLen1 {
1962 | wg.Add(len(res))
1963 | }
1964 |
1965 | for idx1 := range res {
1966 | idx1 := idx1
1967 | rctx := &graphql.ResolverContext{
1968 | Index: &idx1,
1969 | Result: &res[idx1],
1970 | }
1971 | ctx := graphql.WithResolverContext(ctx, rctx)
1972 | f := func(idx1 int) {
1973 | if !isLen1 {
1974 | defer wg.Done()
1975 | }
1976 | arr1[idx1] = func() graphql.Marshaler {
1977 |
1978 | return ec.___EnumValue(ctx, field.Selections, &res[idx1])
1979 | }()
1980 | }
1981 | if isLen1 {
1982 | f(idx1)
1983 | } else {
1984 | go f(idx1)
1985 | }
1986 |
1987 | }
1988 | wg.Wait()
1989 | return arr1
1990 | }
1991 |
1992 | // nolint: vetshadow
1993 | func (ec *executionContext) ___Type_inputFields(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
1994 | rctx := &graphql.ResolverContext{
1995 | Object: "__Type",
1996 | Args: nil,
1997 | Field: field,
1998 | }
1999 | ctx = graphql.WithResolverContext(ctx, rctx)
2000 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
2001 | return obj.InputFields(), nil
2002 | })
2003 | if resTmp == nil {
2004 | return graphql.Null
2005 | }
2006 | res := resTmp.([]introspection.InputValue)
2007 | rctx.Result = res
2008 |
2009 | arr1 := make(graphql.Array, len(res))
2010 | var wg sync.WaitGroup
2011 |
2012 | isLen1 := len(res) == 1
2013 | if !isLen1 {
2014 | wg.Add(len(res))
2015 | }
2016 |
2017 | for idx1 := range res {
2018 | idx1 := idx1
2019 | rctx := &graphql.ResolverContext{
2020 | Index: &idx1,
2021 | Result: &res[idx1],
2022 | }
2023 | ctx := graphql.WithResolverContext(ctx, rctx)
2024 | f := func(idx1 int) {
2025 | if !isLen1 {
2026 | defer wg.Done()
2027 | }
2028 | arr1[idx1] = func() graphql.Marshaler {
2029 |
2030 | return ec.___InputValue(ctx, field.Selections, &res[idx1])
2031 | }()
2032 | }
2033 | if isLen1 {
2034 | f(idx1)
2035 | } else {
2036 | go f(idx1)
2037 | }
2038 |
2039 | }
2040 | wg.Wait()
2041 | return arr1
2042 | }
2043 |
2044 | // nolint: vetshadow
2045 | func (ec *executionContext) ___Type_ofType(ctx context.Context, field graphql.CollectedField, obj *introspection.Type) graphql.Marshaler {
2046 | rctx := &graphql.ResolverContext{
2047 | Object: "__Type",
2048 | Args: nil,
2049 | Field: field,
2050 | }
2051 | ctx = graphql.WithResolverContext(ctx, rctx)
2052 | resTmp := ec.FieldMiddleware(ctx, obj, func(ctx context.Context) (interface{}, error) {
2053 | return obj.OfType(), nil
2054 | })
2055 | if resTmp == nil {
2056 | return graphql.Null
2057 | }
2058 | res := resTmp.(*introspection.Type)
2059 | rctx.Result = res
2060 |
2061 | if res == nil {
2062 | return graphql.Null
2063 | }
2064 |
2065 | return ec.___Type(ctx, field.Selections, res)
2066 | }
2067 |
2068 | func (ec *executionContext) FieldMiddleware(ctx context.Context, obj interface{}, next graphql.Resolver) (ret interface{}) {
2069 | defer func() {
2070 | if r := recover(); r != nil {
2071 | ec.Error(ctx, ec.Recover(ctx, r))
2072 | ret = nil
2073 | }
2074 | }()
2075 | res, err := ec.ResolverMiddleware(ctx, next)
2076 | if err != nil {
2077 | ec.Error(ctx, err)
2078 | return nil
2079 | }
2080 | return res
2081 | }
2082 |
2083 | func (ec *executionContext) introspectSchema() *introspection.Schema {
2084 | return introspection.WrapSchema(parsedSchema)
2085 | }
2086 |
2087 | func (ec *executionContext) introspectType(name string) *introspection.Type {
2088 | return introspection.WrapTypeFromDef(parsedSchema, parsedSchema.Types[name])
2089 | }
2090 |
2091 | var parsedSchema = gqlparser.MustLoadSchema(
2092 | &ast.Source{Name: "schema.graphql", Input: `
2093 | type Channel {
2094 | id: Int! # "!" denotes a required field
2095 | name: String!
2096 | }
2097 |
2098 | type Query {
2099 | channels: [Channel!]!
2100 | }
2101 |
2102 | type Mutation {
2103 | addChannel(name: String!): Channel!
2104 | updateChannel(id:Int!,name: String!): Channel!
2105 | deleteChannel(ID: Int!): Channel!
2106 | }
2107 |
2108 | type Subscription {
2109 | subscriptionChannelAdded: Channel!
2110 | subscriptionChannelDeleted: Channel!
2111 | subscriptionChannelUpdated: Channel!
2112 | }
2113 | `},
2114 | )
2115 |
--------------------------------------------------------------------------------
/golang/app/model/models_gen.go:
--------------------------------------------------------------------------------
1 | // Code generated by github.com/99designs/gqlgen, DO NOT EDIT.
2 |
3 | package model
4 |
5 | type Channel struct {
6 | ID int `json:"id"`
7 | Name string `json:"name"`
8 | }
9 |
--------------------------------------------------------------------------------
/golang/app/resolver/ChannelResolver.go:
--------------------------------------------------------------------------------
1 | package resolver
2 |
3 | import (
4 | context "context"
5 | "golang-gqlgen-reactjs-subscription-demo/golang/app/config/connection"
6 | "golang-gqlgen-reactjs-subscription-demo/golang/app/model"
7 | )
8 |
9 | type channelResolver struct{ *Resolver }
10 |
11 | var addChannelObserver map[string]chan model.Channel
12 | var deleteChannelObserver map[string]chan model.Channel
13 | var updateChannelObserver map[string]chan model.Channel
14 |
15 | func init() {
16 | addChannelObserver = map[string]chan model.Channel{}
17 | deleteChannelObserver = map[string]chan model.Channel{}
18 | updateChannelObserver = map[string]chan model.Channel{}
19 | }
20 | func (r *queryResolver) Channels(ctx context.Context) ([]model.Channel, error) {
21 | db := connection.DbConn()
22 | var query = "SELECT * FROM channel"
23 | selDB, err := db.Query(query)
24 | var arrChannel []model.Channel
25 | for selDB.Next() {
26 | var name string
27 | var id int64
28 | err = selDB.Scan(&id, &name)
29 | if err != nil {
30 | panic(err.Error())
31 | }
32 | todo1 := model.Channel{ID: int(id), Name: name}
33 | arrChannel = append(arrChannel, todo1)
34 | }
35 |
36 | defer db.Close()
37 | return arrChannel, nil
38 | }
39 |
40 | func (r *mutationResolver) AddChannel(ctx context.Context, name string) (model.Channel, error) {
41 | db := connection.DbConn()
42 |
43 | insForm, err := db.Prepare("INSERT INTO channel(name) VALUES(?)")
44 | if err != nil {
45 | panic(err.Error())
46 | }
47 |
48 | var newChannel model.Channel
49 | res, err := insForm.Exec(name)
50 | if err != nil {
51 | println("Exec err:", err.Error())
52 | } else {
53 | var id int64
54 | id, err := res.LastInsertId()
55 | if err != nil {
56 | println("Error:", err.Error())
57 | } else {
58 | newChannel = model.Channel{ID: int(id), Name: name}
59 | }
60 | }
61 | defer db.Close()
62 | //add new chanel in observer
63 | for _, observer := range addChannelObserver {
64 | observer <- newChannel
65 | }
66 | return newChannel, nil
67 | }
68 | func (r *mutationResolver) DeleteChannel(ctx context.Context, ID int) (model.Channel, error) {
69 | db := connection.DbConn()
70 |
71 | delForm, err := db.Prepare("DELETE FROM channel WHERE id=?")
72 | if err != nil {
73 | panic(err.Error())
74 | }
75 | delForm.Exec(ID)
76 | var newChannel model.Channel
77 | defer db.Close()
78 | newChannel = model.Channel{ID: ID, Name: ""}
79 | for _, observer := range deleteChannelObserver {
80 | observer <- newChannel
81 | }
82 | return newChannel, nil
83 | }
84 | func (r *mutationResolver) UpdateChannel(ctx context.Context, id int, name string) (model.Channel, error) {
85 | db := connection.DbConn()
86 |
87 | insForm, err := db.Prepare("UPDATE channel SET name=? WHERE id=?")
88 | if err != nil {
89 | panic(err.Error())
90 | }
91 |
92 | var newChannel model.Channel
93 | insForm.Exec(name, id)
94 | newChannel = model.Channel{ID: id, Name: name}
95 |
96 | defer db.Close()
97 | //add new chanel in observer
98 | for _, observer := range updateChannelObserver {
99 | observer <- newChannel
100 | }
101 | return newChannel, nil
102 | }
103 |
104 | func (r *subscriptionResolver) SubscriptionChannelAdded(ctx context.Context) (<-chan model.Channel, error) {
105 | id := randString(8)
106 | events := make(chan model.Channel, 1)
107 |
108 | go func() {
109 | <-ctx.Done()
110 | delete(addChannelObserver, id)
111 | }()
112 |
113 | addChannelObserver[id] = events
114 |
115 | return events, nil
116 | }
117 |
118 | func (r *subscriptionResolver) SubscriptionChannelDeleted(ctx context.Context) (<-chan model.Channel, error) {
119 | id := randString(8)
120 | events := make(chan model.Channel, 1)
121 |
122 | go func() {
123 | <-ctx.Done()
124 | delete(deleteChannelObserver, id)
125 | }()
126 |
127 | deleteChannelObserver[id] = events
128 |
129 | return events, nil
130 | }
131 |
132 | func (r *subscriptionResolver) SubscriptionChannelUpdated(ctx context.Context) (<-chan model.Channel, error) {
133 | id := randString(8)
134 | events := make(chan model.Channel, 1)
135 |
136 | go func() {
137 | <-ctx.Done()
138 | delete(updateChannelObserver, id)
139 | }()
140 |
141 | updateChannelObserver[id] = events
142 |
143 | return events, nil
144 | }
145 |
--------------------------------------------------------------------------------
/golang/app/resolver/resolver.go:
--------------------------------------------------------------------------------
1 | //go:generate gorunpkg github.com/99designs/gqlgen
2 |
3 | package resolver
4 |
5 | import (
6 | graph "golang-gqlgen-reactjs-subscription-demo/golang/app/graph"
7 | "math/rand"
8 | )
9 |
10 | type Resolver struct{}
11 |
12 | func (r *Resolver) Mutation() graph.MutationResolver {
13 | return &mutationResolver{r}
14 | }
15 | func (r *Resolver) Query() graph.QueryResolver {
16 | return &queryResolver{r}
17 | }
18 | func (r *Resolver) Subscription() graph.SubscriptionResolver {
19 | return &subscriptionResolver{r}
20 | }
21 |
22 | type mutationResolver struct{ *Resolver }
23 |
24 | type queryResolver struct{ *Resolver }
25 |
26 | type subscriptionResolver struct{ *Resolver }
27 |
28 | var letterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")
29 |
30 | func randString(n int) string {
31 | b := make([]rune, n)
32 | for i := range b {
33 | b[i] = letterRunes[rand.Intn(len(letterRunes))]
34 | }
35 | return string(b)
36 | }
37 |
--------------------------------------------------------------------------------
/golang/gqlgen.yml:
--------------------------------------------------------------------------------
1 | # .gqlgen.yml example
2 | #
3 | # Refer to https://gqlgen.com/config/
4 | # for detailed .gqlgen.yml documentation.
5 |
6 | schema: schema.graphql
7 | exec:
8 | filename: app/graph/generated.go
9 |
10 | model:
11 | filename: app/model/models_gen.go
12 |
13 | resolver:
14 | filename: app/resolver/resolver.go
15 | type: Resolver
16 |
--------------------------------------------------------------------------------
/golang/main.go:
--------------------------------------------------------------------------------
1 | package main
2 |
3 | import (
4 | graph "golang-gqlgen-reactjs-subscription-demo/golang/app/graph"
5 | resolver "golang-gqlgen-reactjs-subscription-demo/golang/app/resolver"
6 | "log"
7 | "net/http"
8 | "os"
9 |
10 | "github.com/99designs/gqlgen/handler"
11 | gqlopentracing "github.com/99designs/gqlgen/opentracing"
12 | "github.com/gorilla/websocket"
13 | )
14 |
15 | const defaultPort = "8888"
16 |
17 | func main() {
18 | port := os.Getenv("PORT")
19 | if port == "" {
20 | port = defaultPort
21 | }
22 |
23 | http.Handle("/", handler.Playground("GraphQL playground", "/query"))
24 | // http.Handle("/query", handler.GraphQL(graph.NewExecutableSchema(graph.Config{Resolvers: &resolver.Resolver{}})))
25 | http.Handle("/query", corsAccess(handler.GraphQL(graph.NewExecutableSchema(graph.Config{Resolvers: &resolver.Resolver{}}),
26 |
27 | handler.ResolverMiddleware(gqlopentracing.ResolverMiddleware()),
28 | handler.RequestMiddleware(gqlopentracing.RequestMiddleware()),
29 | handler.WebsocketUpgrader(websocket.Upgrader{
30 | CheckOrigin: func(r *http.Request) bool {
31 | return true
32 | },
33 | }))),
34 | )
35 | log.Printf("connect to http://localhost:%s/ for GraphQL playground", port)
36 | log.Fatal(http.ListenAndServe(":"+port, nil))
37 | }
38 | func corsAccess(next http.HandlerFunc) http.HandlerFunc {
39 | return http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {
40 | w.Header().Set("Access-Control-Allow-Origin", "*")
41 | w.Header().Set("Access-Control-Allow-Credentials", "true")
42 | w.Header().Set("Access-Control-Allow-Methods", "POST, GET, OPTIONS, PUT, DELETE")
43 | w.Header().Set("Access-Control-Allow-Headers",
44 | "Accept, Content-Type, Content-Length, Accept-Encoding, X-CSRF-Token, Authorization")
45 | if req.Method == "OPTIONS" {
46 | return
47 | }
48 | next(w, req)
49 | })
50 | }
51 |
--------------------------------------------------------------------------------
/golang/schema.graphql:
--------------------------------------------------------------------------------
1 |
2 | type Channel {
3 | id: Int! # "!" denotes a required field
4 | name: String!
5 | }
6 |
7 | type Query {
8 | channels: [Channel!]!
9 | }
10 |
11 | type Mutation {
12 | addChannel(name: String!): Channel!
13 | updateChannel(id:Int!,name: String!): Channel!
14 | deleteChannel(ID: Int!): Channel!
15 | }
16 |
17 | type Subscription {
18 | subscriptionChannelAdded: Channel!
19 | subscriptionChannelDeleted: Channel!
20 | subscriptionChannelUpdated: Channel!
21 | }
22 |
--------------------------------------------------------------------------------
/reactjs/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "chat",
3 | "version": "0.1.0",
4 | "private": true,
5 | "dependencies": {
6 | "apollo-boost": "^0.1.15",
7 | "apollo-cache-inmemory": "^1.2.9",
8 | "apollo-client": "^2.4.1",
9 | "apollo-link-ws": "^1.0.8",
10 | "graphql": "^14.0.0",
11 | "graphql-tag": "^2.9.2",
12 | "jwt-decode": "^2.2.0",
13 | "react": "^16.4.2",
14 | "react-apollo": "^2.1.11",
15 | "react-autocomplete": "^1.8.1",
16 | "react-dom": "^16.4.2",
17 | "react-json-view": "^1.19.1",
18 | "react-scripts": "1.1.5",
19 | "subscriptions-transport-ws": "^0.9.14"
20 | },
21 | "scripts": {
22 | "start": "react-scripts start",
23 | "build": "react-scripts build",
24 | "test": "react-scripts test --env=jsdom",
25 | "eject": "react-scripts eject"
26 | },
27 | "devDependencies": {
28 | "axios": "^0.18.0",
29 | "react-addons-update": "^15.6.2",
30 | "react-router-dom": "^4.3.1",
31 | "underscore": "^1.9.1"
32 | }
33 | }
34 |
--------------------------------------------------------------------------------
/reactjs/public/css/dataTables.bootstrap4.min.css:
--------------------------------------------------------------------------------
1 | table.dataTable{clear:both;margin-top:6px !important;margin-bottom:6px !important;max-width:none !important;border-collapse:separate !important;border-spacing:0}table.dataTable td,table.dataTable th{-webkit-box-sizing:content-box;box-sizing:content-box}table.dataTable td.dataTables_empty,table.dataTable th.dataTables_empty{text-align:center}table.dataTable.nowrap th,table.dataTable.nowrap td{white-space:nowrap}div.dataTables_wrapper div.dataTables_length label{font-weight:normal;text-align:left;white-space:nowrap}div.dataTables_wrapper div.dataTables_length select{width:auto;display:inline-block}div.dataTables_wrapper div.dataTables_filter{text-align:right}div.dataTables_wrapper div.dataTables_filter label{font-weight:normal;white-space:nowrap;text-align:left}div.dataTables_wrapper div.dataTables_filter input{margin-left:0.5em;display:inline-block;width:auto}div.dataTables_wrapper div.dataTables_info{padding-top:0.85em;white-space:nowrap}div.dataTables_wrapper div.dataTables_paginate{margin:0;white-space:nowrap;text-align:right}div.dataTables_wrapper div.dataTables_paginate ul.pagination{margin:2px 0;white-space:nowrap;justify-content:flex-end}div.dataTables_wrapper div.dataTables_processing{position:absolute;top:50%;left:50%;width:200px;margin-left:-100px;margin-top:-26px;text-align:center;padding:1em 0}table.dataTable thead>tr>th.sorting_asc,table.dataTable thead>tr>th.sorting_desc,table.dataTable thead>tr>th.sorting,table.dataTable thead>tr>td.sorting_asc,table.dataTable thead>tr>td.sorting_desc,table.dataTable thead>tr>td.sorting{padding-right:30px}table.dataTable thead>tr>th:active,table.dataTable thead>tr>td:active{outline:none}table.dataTable thead .sorting,table.dataTable thead .sorting_asc,table.dataTable thead .sorting_desc,table.dataTable thead .sorting_asc_disabled,table.dataTable thead .sorting_desc_disabled{cursor:pointer;position:relative}table.dataTable thead .sorting:before,table.dataTable thead .sorting:after,table.dataTable thead .sorting_asc:before,table.dataTable thead .sorting_asc:after,table.dataTable thead .sorting_desc:before,table.dataTable thead .sorting_desc:after,table.dataTable thead .sorting_asc_disabled:before,table.dataTable thead .sorting_asc_disabled:after,table.dataTable thead .sorting_desc_disabled:before,table.dataTable thead .sorting_desc_disabled:after{position:absolute;bottom:0.9em;display:block;opacity:0.3}table.dataTable thead .sorting:before,table.dataTable thead .sorting_asc:before,table.dataTable thead .sorting_desc:before,table.dataTable thead .sorting_asc_disabled:before,table.dataTable thead .sorting_desc_disabled:before{right:1em;content:"\2191"}table.dataTable thead .sorting:after,table.dataTable thead .sorting_asc:after,table.dataTable thead .sorting_desc:after,table.dataTable thead .sorting_asc_disabled:after,table.dataTable thead .sorting_desc_disabled:after{right:0.5em;content:"\2193"}table.dataTable thead .sorting_asc:before,table.dataTable thead .sorting_desc:after{opacity:1}table.dataTable thead .sorting_asc_disabled:before,table.dataTable thead .sorting_desc_disabled:after{opacity:0}div.dataTables_scrollHead table.dataTable{margin-bottom:0 !important}div.dataTables_scrollBody table{border-top:none;margin-top:0 !important;margin-bottom:0 !important}div.dataTables_scrollBody table thead .sorting:before,div.dataTables_scrollBody table thead .sorting_asc:before,div.dataTables_scrollBody table thead .sorting_desc:before,div.dataTables_scrollBody table thead .sorting:after,div.dataTables_scrollBody table thead .sorting_asc:after,div.dataTables_scrollBody table thead .sorting_desc:after{display:none}div.dataTables_scrollBody table tbody tr:first-child th,div.dataTables_scrollBody table tbody tr:first-child td{border-top:none}div.dataTables_scrollFoot>.dataTables_scrollFootInner{box-sizing:content-box}div.dataTables_scrollFoot>.dataTables_scrollFootInner>table{margin-top:0 !important;border-top:none}@media screen and (max-width: 767px){div.dataTables_wrapper div.dataTables_length,div.dataTables_wrapper div.dataTables_filter,div.dataTables_wrapper div.dataTables_info,div.dataTables_wrapper div.dataTables_paginate{text-align:center}}table.dataTable.table-sm>thead>tr>th{padding-right:20px}table.dataTable.table-sm .sorting:before,table.dataTable.table-sm .sorting_asc:before,table.dataTable.table-sm .sorting_desc:before{top:5px;right:0.85em}table.dataTable.table-sm .sorting:after,table.dataTable.table-sm .sorting_asc:after,table.dataTable.table-sm .sorting_desc:after{top:5px}table.table-bordered.dataTable th,table.table-bordered.dataTable td{border-left-width:0}table.table-bordered.dataTable th:last-child,table.table-bordered.dataTable th:last-child,table.table-bordered.dataTable td:last-child,table.table-bordered.dataTable td:last-child{border-right-width:0}table.table-bordered.dataTable tbody th,table.table-bordered.dataTable tbody td{border-bottom-width:0}div.dataTables_scrollHead table.table-bordered{border-bottom-width:0}div.table-responsive>div.dataTables_wrapper>div.row{margin:0}div.table-responsive>div.dataTables_wrapper>div.row>div[class^="col-"]:first-child{padding-left:0}div.table-responsive>div.dataTables_wrapper>div.row>div[class^="col-"]:last-child{padding-right:0}
2 |
--------------------------------------------------------------------------------
/reactjs/public/css/datatables.min.css:
--------------------------------------------------------------------------------
1 | /*
2 | * This combined file was created by the DataTables downloader builder:
3 | * https://datatables.net/download
4 | *
5 | * To rebuild or modify this file with the latest versions of the included
6 | * software please visit:
7 | * https://datatables.net/download/#bs4/dt-1.10.18/r-2.2.2
8 | *
9 | * Included libraries:
10 | * DataTables 1.10.18, Responsive 2.2.2
11 | */
12 |
13 | table.dataTable{clear:both;margin-top:6px !important;margin-bottom:6px !important;max-width:none !important;border-collapse:separate !important;border-spacing:0}table.dataTable td,table.dataTable th{-webkit-box-sizing:content-box;box-sizing:content-box}table.dataTable td.dataTables_empty,table.dataTable th.dataTables_empty{text-align:center}table.dataTable.nowrap th,table.dataTable.nowrap td{white-space:nowrap}div.dataTables_wrapper div.dataTables_length label{font-weight:normal;text-align:left;white-space:nowrap}div.dataTables_wrapper div.dataTables_length select{width:auto;display:inline-block}div.dataTables_wrapper div.dataTables_filter{text-align:right}div.dataTables_wrapper div.dataTables_filter label{font-weight:normal;white-space:nowrap;text-align:left}div.dataTables_wrapper div.dataTables_filter input{margin-left:0.5em;display:inline-block;width:auto}div.dataTables_wrapper div.dataTables_info{padding-top:0.85em;white-space:nowrap}div.dataTables_wrapper div.dataTables_paginate{margin:0;white-space:nowrap;text-align:right}div.dataTables_wrapper div.dataTables_paginate ul.pagination{margin:2px 0;white-space:nowrap;justify-content:flex-end}div.dataTables_wrapper div.dataTables_processing{position:absolute;top:50%;left:50%;width:200px;margin-left:-100px;margin-top:-26px;text-align:center;padding:1em 0}table.dataTable thead>tr>th.sorting_asc,table.dataTable thead>tr>th.sorting_desc,table.dataTable thead>tr>th.sorting,table.dataTable thead>tr>td.sorting_asc,table.dataTable thead>tr>td.sorting_desc,table.dataTable thead>tr>td.sorting{padding-right:30px}table.dataTable thead>tr>th:active,table.dataTable thead>tr>td:active{outline:none}table.dataTable thead .sorting,table.dataTable thead .sorting_asc,table.dataTable thead .sorting_desc,table.dataTable thead .sorting_asc_disabled,table.dataTable thead .sorting_desc_disabled{cursor:pointer;position:relative}table.dataTable thead .sorting:before,table.dataTable thead .sorting:after,table.dataTable thead .sorting_asc:before,table.dataTable thead .sorting_asc:after,table.dataTable thead .sorting_desc:before,table.dataTable thead .sorting_desc:after,table.dataTable thead .sorting_asc_disabled:before,table.dataTable thead .sorting_asc_disabled:after,table.dataTable thead .sorting_desc_disabled:before,table.dataTable thead .sorting_desc_disabled:after{position:absolute;bottom:0.9em;display:block;opacity:0.3}table.dataTable thead .sorting:before,table.dataTable thead .sorting_asc:before,table.dataTable thead .sorting_desc:before,table.dataTable thead .sorting_asc_disabled:before,table.dataTable thead .sorting_desc_disabled:before{right:1em;content:"\2191"}table.dataTable thead .sorting:after,table.dataTable thead .sorting_asc:after,table.dataTable thead .sorting_desc:after,table.dataTable thead .sorting_asc_disabled:after,table.dataTable thead .sorting_desc_disabled:after{right:0.5em;content:"\2193"}table.dataTable thead .sorting_asc:before,table.dataTable thead .sorting_desc:after{opacity:1}table.dataTable thead .sorting_asc_disabled:before,table.dataTable thead .sorting_desc_disabled:after{opacity:0}div.dataTables_scrollHead table.dataTable{margin-bottom:0 !important}div.dataTables_scrollBody table{border-top:none;margin-top:0 !important;margin-bottom:0 !important}div.dataTables_scrollBody table thead .sorting:before,div.dataTables_scrollBody table thead .sorting_asc:before,div.dataTables_scrollBody table thead .sorting_desc:before,div.dataTables_scrollBody table thead .sorting:after,div.dataTables_scrollBody table thead .sorting_asc:after,div.dataTables_scrollBody table thead .sorting_desc:after{display:none}div.dataTables_scrollBody table tbody tr:first-child th,div.dataTables_scrollBody table tbody tr:first-child td{border-top:none}div.dataTables_scrollFoot>.dataTables_scrollFootInner{box-sizing:content-box}div.dataTables_scrollFoot>.dataTables_scrollFootInner>table{margin-top:0 !important;border-top:none}@media screen and (max-width: 767px){div.dataTables_wrapper div.dataTables_length,div.dataTables_wrapper div.dataTables_filter,div.dataTables_wrapper div.dataTables_info,div.dataTables_wrapper div.dataTables_paginate{text-align:center}}table.dataTable.table-sm>thead>tr>th{padding-right:20px}table.dataTable.table-sm .sorting:before,table.dataTable.table-sm .sorting_asc:before,table.dataTable.table-sm .sorting_desc:before{top:5px;right:0.85em}table.dataTable.table-sm .sorting:after,table.dataTable.table-sm .sorting_asc:after,table.dataTable.table-sm .sorting_desc:after{top:5px}table.table-bordered.dataTable th,table.table-bordered.dataTable td{border-left-width:0}table.table-bordered.dataTable th:last-child,table.table-bordered.dataTable th:last-child,table.table-bordered.dataTable td:last-child,table.table-bordered.dataTable td:last-child{border-right-width:0}table.table-bordered.dataTable tbody th,table.table-bordered.dataTable tbody td{border-bottom-width:0}div.dataTables_scrollHead table.table-bordered{border-bottom-width:0}div.table-responsive>div.dataTables_wrapper>div.row{margin:0}div.table-responsive>div.dataTables_wrapper>div.row>div[class^="col-"]:first-child{padding-left:0}div.table-responsive>div.dataTables_wrapper>div.row>div[class^="col-"]:last-child{padding-right:0}
14 |
15 |
16 | table.dataTable.dtr-inline.collapsed>tbody>tr>td.child,table.dataTable.dtr-inline.collapsed>tbody>tr>th.child,table.dataTable.dtr-inline.collapsed>tbody>tr>td.dataTables_empty{cursor:default !important}table.dataTable.dtr-inline.collapsed>tbody>tr>td.child:before,table.dataTable.dtr-inline.collapsed>tbody>tr>th.child:before,table.dataTable.dtr-inline.collapsed>tbody>tr>td.dataTables_empty:before{display:none !important}table.dataTable.dtr-inline.collapsed>tbody>tr[role="row"]>td:first-child,table.dataTable.dtr-inline.collapsed>tbody>tr[role="row"]>th:first-child{position:relative;padding-left:30px;cursor:pointer}table.dataTable.dtr-inline.collapsed>tbody>tr[role="row"]>td:first-child:before,table.dataTable.dtr-inline.collapsed>tbody>tr[role="row"]>th:first-child:before{top:12px;left:4px;height:14px;width:14px;display:block;position:absolute;color:white;border:2px solid white;border-radius:14px;box-shadow:0 0 3px #444;box-sizing:content-box;text-align:center;text-indent:0 !important;font-family:'Courier New', Courier, monospace;line-height:14px;content:'+';background-color:#0275d8}table.dataTable.dtr-inline.collapsed>tbody>tr.parent>td:first-child:before,table.dataTable.dtr-inline.collapsed>tbody>tr.parent>th:first-child:before{content:'-';background-color:#d33333}table.dataTable.dtr-inline.collapsed.compact>tbody>tr>td:first-child,table.dataTable.dtr-inline.collapsed.compact>tbody>tr>th:first-child{padding-left:27px}table.dataTable.dtr-inline.collapsed.compact>tbody>tr>td:first-child:before,table.dataTable.dtr-inline.collapsed.compact>tbody>tr>th:first-child:before{top:5px;left:4px;height:14px;width:14px;border-radius:14px;line-height:14px;text-indent:3px}table.dataTable.dtr-column>tbody>tr>td.control,table.dataTable.dtr-column>tbody>tr>th.control{position:relative;cursor:pointer}table.dataTable.dtr-column>tbody>tr>td.control:before,table.dataTable.dtr-column>tbody>tr>th.control:before{top:50%;left:50%;height:16px;width:16px;margin-top:-10px;margin-left:-10px;display:block;position:absolute;color:white;border:2px solid white;border-radius:14px;box-shadow:0 0 3px #444;box-sizing:content-box;text-align:center;text-indent:0 !important;font-family:'Courier New', Courier, monospace;line-height:14px;content:'+';background-color:#0275d8}table.dataTable.dtr-column>tbody>tr.parent td.control:before,table.dataTable.dtr-column>tbody>tr.parent th.control:before{content:'-';background-color:#d33333}table.dataTable>tbody>tr.child{padding:0.5em 1em}table.dataTable>tbody>tr.child:hover{background:transparent !important}table.dataTable>tbody>tr.child ul.dtr-details{display:inline-block;list-style-type:none;margin:0;padding:0}table.dataTable>tbody>tr.child ul.dtr-details>li{border-bottom:1px solid #efefef;padding:0.5em 0}table.dataTable>tbody>tr.child ul.dtr-details>li:first-child{padding-top:0}table.dataTable>tbody>tr.child ul.dtr-details>li:last-child{border-bottom:none}table.dataTable>tbody>tr.child span.dtr-title{display:inline-block;min-width:75px;font-weight:bold}div.dtr-modal{position:fixed;box-sizing:border-box;top:0;left:0;height:100%;width:100%;z-index:100;padding:10em 1em}div.dtr-modal div.dtr-modal-display{position:absolute;top:0;left:0;bottom:0;right:0;width:50%;height:50%;overflow:auto;margin:auto;z-index:102;overflow:auto;background-color:#f5f5f7;border:1px solid black;border-radius:0.5em;box-shadow:0 12px 30px rgba(0,0,0,0.6)}div.dtr-modal div.dtr-modal-content{position:relative;padding:1em}div.dtr-modal div.dtr-modal-close{position:absolute;top:6px;right:6px;width:22px;height:22px;border:1px solid #eaeaea;background-color:#f9f9f9;text-align:center;border-radius:3px;cursor:pointer;z-index:12}div.dtr-modal div.dtr-modal-close:hover{background-color:#eaeaea}div.dtr-modal div.dtr-modal-background{position:fixed;top:0;left:0;right:0;bottom:0;z-index:101;background:rgba(0,0,0,0.6)}@media screen and (max-width: 767px){div.dtr-modal div.dtr-modal-display{width:95%}}div.dtr-bs-modal table.table tr:first-child td{border-top:none}
17 |
18 |
19 |
--------------------------------------------------------------------------------
/reactjs/public/css/loader.css:
--------------------------------------------------------------------------------
1 |
2 |
3 | .lds-roller {
4 | display: inline-block;
5 | position: relative;
6 | width: 64px;
7 | height: 64px;
8 | top:250px
9 | }
10 | .lds-roller div {
11 | animation: lds-roller 1.2s cubic-bezier(0.5, 0, 0.5, 1) infinite;
12 | transform-origin: 32px 32px;
13 | }
14 | .lds-roller div:after {
15 | content: " ";
16 | display: block;
17 | position: absolute;
18 | width: 6px;
19 | height: 6px;
20 | border-radius: 50%;
21 | background: black;
22 | margin: -3px 0 0 -3px;
23 | }
24 | .lds-roller div:nth-child(1) {
25 | animation-delay: -0.036s;
26 | }
27 | .lds-roller div:nth-child(1):after {
28 | top: 50px;
29 | left: 50px;
30 | }
31 | .lds-roller div:nth-child(2) {
32 | animation-delay: -0.072s;
33 | }
34 | .lds-roller div:nth-child(2):after {
35 | top: 54px;
36 | left: 45px;
37 | }
38 | .lds-roller div:nth-child(3) {
39 | animation-delay: -0.108s;
40 | }
41 | .lds-roller div:nth-child(3):after {
42 | top: 57px;
43 | left: 39px;
44 | }
45 | .lds-roller div:nth-child(4) {
46 | animation-delay: -0.144s;
47 | }
48 | .lds-roller div:nth-child(4):after {
49 | top: 58px;
50 | left: 32px;
51 | }
52 | .lds-roller div:nth-child(5) {
53 | animation-delay: -0.18s;
54 | }
55 | .lds-roller div:nth-child(5):after {
56 | top: 57px;
57 | left: 25px;
58 | }
59 | .lds-roller div:nth-child(6) {
60 | animation-delay: -0.216s;
61 | }
62 | .lds-roller div:nth-child(6):after {
63 | top: 54px;
64 | left: 19px;
65 | }
66 | .lds-roller div:nth-child(7) {
67 | animation-delay: -0.252s;
68 | }
69 | .lds-roller div:nth-child(7):after {
70 | top: 50px;
71 | left: 14px;
72 | }
73 | .lds-roller div:nth-child(8) {
74 | animation-delay: -0.288s;
75 | }
76 | .lds-roller div:nth-child(8):after {
77 | top: 45px;
78 | left: 10px;
79 | }
80 | @keyframes lds-roller {
81 | 0% {
82 | transform: rotate(0deg);
83 | }
84 | 100% {
85 | transform: rotate(360deg);
86 | }
87 | }
88 |
--------------------------------------------------------------------------------
/reactjs/public/img/3pl-logo-600.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/3pl-logo-600.png
--------------------------------------------------------------------------------
/reactjs/public/img/favicon-16x16.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/favicon-16x16.png
--------------------------------------------------------------------------------
/reactjs/public/img/favicon-32x32.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/favicon-32x32.png
--------------------------------------------------------------------------------
/reactjs/public/img/green.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/green.png
--------------------------------------------------------------------------------
/reactjs/public/img/red.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/red.png
--------------------------------------------------------------------------------
/reactjs/public/img/yellow.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/yellow.jpg
--------------------------------------------------------------------------------
/reactjs/public/img/yellow.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/logisticinfotech/golang-gqlgen-reactjs-subscription-demo/003342486bfe2767bdfe3cda11474a5d7f669b3a/reactjs/public/img/yellow.png
--------------------------------------------------------------------------------
/reactjs/public/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 | React App
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
26 |
27 |
28 |
29 |
--------------------------------------------------------------------------------
/reactjs/public/js/bootstrap.min.js:
--------------------------------------------------------------------------------
1 | /*!
2 | * Bootstrap v4.0.0 (https://getbootstrap.com)
3 | * Copyright 2011-2018 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors)
4 | * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
5 | */
6 | !function(t,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports,require("jquery"),require("popper.js")):"function"==typeof define&&define.amd?define(["exports","jquery","popper.js"],e):e(t.bootstrap={},t.jQuery,t.Popper)}(this,function(t,e,n){"use strict";function i(t,e){for(var n=0;n0?i:null}catch(t){return null}},reflow:function(t){return t.offsetHeight},triggerTransitionEnd:function(n){t(n).trigger(e.end)},supportsTransitionEnd:function(){return Boolean(e)},isElement:function(t){return(t[0]||t).nodeType},typeCheckConfig:function(t,e,n){for(var s in n)if(Object.prototype.hasOwnProperty.call(n,s)){var r=n[s],o=e[s],a=o&&i.isElement(o)?"element":(l=o,{}.toString.call(l).match(/\s([a-zA-Z]+)/)[1].toLowerCase());if(!new RegExp(r).test(a))throw new Error(t.toUpperCase()+': Option "'+s+'" provided type "'+a+'" but expected type "'+r+'".')}var l}};return e=("undefined"==typeof window||!window.QUnit)&&{end:"transitionend"},t.fn.emulateTransitionEnd=n,i.supportsTransitionEnd()&&(t.event.special[i.TRANSITION_END]={bindType:e.end,delegateType:e.end,handle:function(e){if(t(e.target).is(this))return e.handleObj.handler.apply(this,arguments)}}),i}(e),L=(a="alert",h="."+(l="bs.alert"),c=(o=e).fn[a],u={CLOSE:"close"+h,CLOSED:"closed"+h,CLICK_DATA_API:"click"+h+".data-api"},f="alert",d="fade",_="show",g=function(){function t(t){this._element=t}var e=t.prototype;return e.close=function(t){t=t||this._element;var e=this._getRootElement(t);this._triggerCloseEvent(e).isDefaultPrevented()||this._removeElement(e)},e.dispose=function(){o.removeData(this._element,l),this._element=null},e._getRootElement=function(t){var e=P.getSelectorFromElement(t),n=!1;return e&&(n=o(e)[0]),n||(n=o(t).closest("."+f)[0]),n},e._triggerCloseEvent=function(t){var e=o.Event(u.CLOSE);return o(t).trigger(e),e},e._removeElement=function(t){var e=this;o(t).removeClass(_),P.supportsTransitionEnd()&&o(t).hasClass(d)?o(t).one(P.TRANSITION_END,function(n){return e._destroyElement(t,n)}).emulateTransitionEnd(150):this._destroyElement(t)},e._destroyElement=function(t){o(t).detach().trigger(u.CLOSED).remove()},t._jQueryInterface=function(e){return this.each(function(){var n=o(this),i=n.data(l);i||(i=new t(this),n.data(l,i)),"close"===e&&i[e](this)})},t._handleDismiss=function(t){return function(e){e&&e.preventDefault(),t.close(this)}},s(t,null,[{key:"VERSION",get:function(){return"4.0.0"}}]),t}(),o(document).on(u.CLICK_DATA_API,'[data-dismiss="alert"]',g._handleDismiss(new g)),o.fn[a]=g._jQueryInterface,o.fn[a].Constructor=g,o.fn[a].noConflict=function(){return o.fn[a]=c,g._jQueryInterface},g),R=(m="button",E="."+(v="bs.button"),T=".data-api",y=(p=e).fn[m],C="active",I="btn",A="focus",b='[data-toggle^="button"]',D='[data-toggle="buttons"]',S="input",w=".active",N=".btn",O={CLICK_DATA_API:"click"+E+T,FOCUS_BLUR_DATA_API:"focus"+E+T+" blur"+E+T},k=function(){function t(t){this._element=t}var e=t.prototype;return e.toggle=function(){var t=!0,e=!0,n=p(this._element).closest(D)[0];if(n){var i=p(this._element).find(S)[0];if(i){if("radio"===i.type)if(i.checked&&p(this._element).hasClass(C))t=!1;else{var s=p(n).find(w)[0];s&&p(s).removeClass(C)}if(t){if(i.hasAttribute("disabled")||n.hasAttribute("disabled")||i.classList.contains("disabled")||n.classList.contains("disabled"))return;i.checked=!p(this._element).hasClass(C),p(i).trigger("change")}i.focus(),e=!1}}e&&this._element.setAttribute("aria-pressed",!p(this._element).hasClass(C)),t&&p(this._element).toggleClass(C)},e.dispose=function(){p.removeData(this._element,v),this._element=null},t._jQueryInterface=function(e){return this.each(function(){var n=p(this).data(v);n||(n=new t(this),p(this).data(v,n)),"toggle"===e&&n[e]()})},s(t,null,[{key:"VERSION",get:function(){return"4.0.0"}}]),t}(),p(document).on(O.CLICK_DATA_API,b,function(t){t.preventDefault();var e=t.target;p(e).hasClass(I)||(e=p(e).closest(N)),k._jQueryInterface.call(p(e),"toggle")}).on(O.FOCUS_BLUR_DATA_API,b,function(t){var e=p(t.target).closest(N)[0];p(e).toggleClass(A,/^focus(in)?$/.test(t.type))}),p.fn[m]=k._jQueryInterface,p.fn[m].Constructor=k,p.fn[m].noConflict=function(){return p.fn[m]=y,k._jQueryInterface},k),j=function(t){var e="carousel",n="bs.carousel",i="."+n,o=t.fn[e],a={interval:5e3,keyboard:!0,slide:!1,pause:"hover",wrap:!0},l={interval:"(number|boolean)",keyboard:"boolean",slide:"(boolean|string)",pause:"(string|boolean)",wrap:"boolean"},h="next",c="prev",u="left",f="right",d={SLIDE:"slide"+i,SLID:"slid"+i,KEYDOWN:"keydown"+i,MOUSEENTER:"mouseenter"+i,MOUSELEAVE:"mouseleave"+i,TOUCHEND:"touchend"+i,LOAD_DATA_API:"load"+i+".data-api",CLICK_DATA_API:"click"+i+".data-api"},_="carousel",g="active",p="slide",m="carousel-item-right",v="carousel-item-left",E="carousel-item-next",T="carousel-item-prev",y={ACTIVE:".active",ACTIVE_ITEM:".active.carousel-item",ITEM:".carousel-item",NEXT_PREV:".carousel-item-next, .carousel-item-prev",INDICATORS:".carousel-indicators",DATA_SLIDE:"[data-slide], [data-slide-to]",DATA_RIDE:'[data-ride="carousel"]'},C=function(){function o(e,n){this._items=null,this._interval=null,this._activeElement=null,this._isPaused=!1,this._isSliding=!1,this.touchTimeout=null,this._config=this._getConfig(n),this._element=t(e)[0],this._indicatorsElement=t(this._element).find(y.INDICATORS)[0],this._addEventListeners()}var C=o.prototype;return C.next=function(){this._isSliding||this._slide(h)},C.nextWhenVisible=function(){!document.hidden&&t(this._element).is(":visible")&&"hidden"!==t(this._element).css("visibility")&&this.next()},C.prev=function(){this._isSliding||this._slide(c)},C.pause=function(e){e||(this._isPaused=!0),t(this._element).find(y.NEXT_PREV)[0]&&P.supportsTransitionEnd()&&(P.triggerTransitionEnd(this._element),this.cycle(!0)),clearInterval(this._interval),this._interval=null},C.cycle=function(t){t||(this._isPaused=!1),this._interval&&(clearInterval(this._interval),this._interval=null),this._config.interval&&!this._isPaused&&(this._interval=setInterval((document.visibilityState?this.nextWhenVisible:this.next).bind(this),this._config.interval))},C.to=function(e){var n=this;this._activeElement=t(this._element).find(y.ACTIVE_ITEM)[0];var i=this._getItemIndex(this._activeElement);if(!(e>this._items.length-1||e<0))if(this._isSliding)t(this._element).one(d.SLID,function(){return n.to(e)});else{if(i===e)return this.pause(),void this.cycle();var s=e>i?h:c;this._slide(s,this._items[e])}},C.dispose=function(){t(this._element).off(i),t.removeData(this._element,n),this._items=null,this._config=null,this._element=null,this._interval=null,this._isPaused=null,this._isSliding=null,this._activeElement=null,this._indicatorsElement=null},C._getConfig=function(t){return t=r({},a,t),P.typeCheckConfig(e,t,l),t},C._addEventListeners=function(){var e=this;this._config.keyboard&&t(this._element).on(d.KEYDOWN,function(t){return e._keydown(t)}),"hover"===this._config.pause&&(t(this._element).on(d.MOUSEENTER,function(t){return e.pause(t)}).on(d.MOUSELEAVE,function(t){return e.cycle(t)}),"ontouchstart"in document.documentElement&&t(this._element).on(d.TOUCHEND,function(){e.pause(),e.touchTimeout&&clearTimeout(e.touchTimeout),e.touchTimeout=setTimeout(function(t){return e.cycle(t)},500+e._config.interval)}))},C._keydown=function(t){if(!/input|textarea/i.test(t.target.tagName))switch(t.which){case 37:t.preventDefault(),this.prev();break;case 39:t.preventDefault(),this.next()}},C._getItemIndex=function(e){return this._items=t.makeArray(t(e).parent().find(y.ITEM)),this._items.indexOf(e)},C._getItemByDirection=function(t,e){var n=t===h,i=t===c,s=this._getItemIndex(e),r=this._items.length-1;if((i&&0===s||n&&s===r)&&!this._config.wrap)return e;var o=(s+(t===c?-1:1))%this._items.length;return-1===o?this._items[this._items.length-1]:this._items[o]},C._triggerSlideEvent=function(e,n){var i=this._getItemIndex(e),s=this._getItemIndex(t(this._element).find(y.ACTIVE_ITEM)[0]),r=t.Event(d.SLIDE,{relatedTarget:e,direction:n,from:s,to:i});return t(this._element).trigger(r),r},C._setActiveIndicatorElement=function(e){if(this._indicatorsElement){t(this._indicatorsElement).find(y.ACTIVE).removeClass(g);var n=this._indicatorsElement.children[this._getItemIndex(e)];n&&t(n).addClass(g)}},C._slide=function(e,n){var i,s,r,o=this,a=t(this._element).find(y.ACTIVE_ITEM)[0],l=this._getItemIndex(a),c=n||a&&this._getItemByDirection(e,a),_=this._getItemIndex(c),C=Boolean(this._interval);if(e===h?(i=v,s=E,r=u):(i=m,s=T,r=f),c&&t(c).hasClass(g))this._isSliding=!1;else if(!this._triggerSlideEvent(c,r).isDefaultPrevented()&&a&&c){this._isSliding=!0,C&&this.pause(),this._setActiveIndicatorElement(c);var I=t.Event(d.SLID,{relatedTarget:c,direction:r,from:l,to:_});P.supportsTransitionEnd()&&t(this._element).hasClass(p)?(t(c).addClass(s),P.reflow(c),t(a).addClass(i),t(c).addClass(i),t(a).one(P.TRANSITION_END,function(){t(c).removeClass(i+" "+s).addClass(g),t(a).removeClass(g+" "+s+" "+i),o._isSliding=!1,setTimeout(function(){return t(o._element).trigger(I)},0)}).emulateTransitionEnd(600)):(t(a).removeClass(g),t(c).addClass(g),this._isSliding=!1,t(this._element).trigger(I)),C&&this.cycle()}},o._jQueryInterface=function(e){return this.each(function(){var i=t(this).data(n),s=r({},a,t(this).data());"object"==typeof e&&(s=r({},s,e));var l="string"==typeof e?e:s.slide;if(i||(i=new o(this,s),t(this).data(n,i)),"number"==typeof e)i.to(e);else if("string"==typeof l){if("undefined"==typeof i[l])throw new TypeError('No method named "'+l+'"');i[l]()}else s.interval&&(i.pause(),i.cycle())})},o._dataApiClickHandler=function(e){var i=P.getSelectorFromElement(this);if(i){var s=t(i)[0];if(s&&t(s).hasClass(_)){var a=r({},t(s).data(),t(this).data()),l=this.getAttribute("data-slide-to");l&&(a.interval=!1),o._jQueryInterface.call(t(s),a),l&&t(s).data(n).to(l),e.preventDefault()}}},s(o,null,[{key:"VERSION",get:function(){return"4.0.0"}},{key:"Default",get:function(){return a}}]),o}();return t(document).on(d.CLICK_DATA_API,y.DATA_SLIDE,C._dataApiClickHandler),t(window).on(d.LOAD_DATA_API,function(){t(y.DATA_RIDE).each(function(){var e=t(this);C._jQueryInterface.call(e,e.data())})}),t.fn[e]=C._jQueryInterface,t.fn[e].Constructor=C,t.fn[e].noConflict=function(){return t.fn[e]=o,C._jQueryInterface},C}(e),H=function(t){var e="collapse",n="bs.collapse",i="."+n,o=t.fn[e],a={toggle:!0,parent:""},l={toggle:"boolean",parent:"(string|element)"},h={SHOW:"show"+i,SHOWN:"shown"+i,HIDE:"hide"+i,HIDDEN:"hidden"+i,CLICK_DATA_API:"click"+i+".data-api"},c="show",u="collapse",f="collapsing",d="collapsed",_="width",g="height",p={ACTIVES:".show, .collapsing",DATA_TOGGLE:'[data-toggle="collapse"]'},m=function(){function i(e,n){this._isTransitioning=!1,this._element=e,this._config=this._getConfig(n),this._triggerArray=t.makeArray(t('[data-toggle="collapse"][href="#'+e.id+'"],[data-toggle="collapse"][data-target="#'+e.id+'"]'));for(var i=t(p.DATA_TOGGLE),s=0;s0&&(this._selector=o,this._triggerArray.push(r))}this._parent=this._config.parent?this._getParent():null,this._config.parent||this._addAriaAndCollapsedClass(this._element,this._triggerArray),this._config.toggle&&this.toggle()}var o=i.prototype;return o.toggle=function(){t(this._element).hasClass(c)?this.hide():this.show()},o.show=function(){var e,s,r=this;if(!this._isTransitioning&&!t(this._element).hasClass(c)&&(this._parent&&0===(e=t.makeArray(t(this._parent).find(p.ACTIVES).filter('[data-parent="'+this._config.parent+'"]'))).length&&(e=null),!(e&&(s=t(e).not(this._selector).data(n))&&s._isTransitioning))){var o=t.Event(h.SHOW);if(t(this._element).trigger(o),!o.isDefaultPrevented()){e&&(i._jQueryInterface.call(t(e).not(this._selector),"hide"),s||t(e).data(n,null));var a=this._getDimension();t(this._element).removeClass(u).addClass(f),this._element.style[a]=0,this._triggerArray.length>0&&t(this._triggerArray).removeClass(d).attr("aria-expanded",!0),this.setTransitioning(!0);var l=function(){t(r._element).removeClass(f).addClass(u).addClass(c),r._element.style[a]="",r.setTransitioning(!1),t(r._element).trigger(h.SHOWN)};if(P.supportsTransitionEnd()){var _="scroll"+(a[0].toUpperCase()+a.slice(1));t(this._element).one(P.TRANSITION_END,l).emulateTransitionEnd(600),this._element.style[a]=this._element[_]+"px"}else l()}}},o.hide=function(){var e=this;if(!this._isTransitioning&&t(this._element).hasClass(c)){var n=t.Event(h.HIDE);if(t(this._element).trigger(n),!n.isDefaultPrevented()){var i=this._getDimension();if(this._element.style[i]=this._element.getBoundingClientRect()[i]+"px",P.reflow(this._element),t(this._element).addClass(f).removeClass(u).removeClass(c),this._triggerArray.length>0)for(var s=0;s0&&t(n).toggleClass(d,!i).attr("aria-expanded",i)}},i._getTargetFromElement=function(e){var n=P.getSelectorFromElement(e);return n?t(n)[0]:null},i._jQueryInterface=function(e){return this.each(function(){var s=t(this),o=s.data(n),l=r({},a,s.data(),"object"==typeof e&&e);if(!o&&l.toggle&&/show|hide/.test(e)&&(l.toggle=!1),o||(o=new i(this,l),s.data(n,o)),"string"==typeof e){if("undefined"==typeof o[e])throw new TypeError('No method named "'+e+'"');o[e]()}})},s(i,null,[{key:"VERSION",get:function(){return"4.0.0"}},{key:"Default",get:function(){return a}}]),i}();return t(document).on(h.CLICK_DATA_API,p.DATA_TOGGLE,function(e){"A"===e.currentTarget.tagName&&e.preventDefault();var i=t(this),s=P.getSelectorFromElement(this);t(s).each(function(){var e=t(this),s=e.data(n)?"toggle":i.data();m._jQueryInterface.call(e,s)})}),t.fn[e]=m._jQueryInterface,t.fn[e].Constructor=m,t.fn[e].noConflict=function(){return t.fn[e]=o,m._jQueryInterface},m}(e),W=function(t){var e="dropdown",i="bs.dropdown",o="."+i,a=".data-api",l=t.fn[e],h=new RegExp("38|40|27"),c={HIDE:"hide"+o,HIDDEN:"hidden"+o,SHOW:"show"+o,SHOWN:"shown"+o,CLICK:"click"+o,CLICK_DATA_API:"click"+o+a,KEYDOWN_DATA_API:"keydown"+o+a,KEYUP_DATA_API:"keyup"+o+a},u="disabled",f="show",d="dropup",_="dropright",g="dropleft",p="dropdown-menu-right",m="dropdown-menu-left",v="position-static",E='[data-toggle="dropdown"]',T=".dropdown form",y=".dropdown-menu",C=".navbar-nav",I=".dropdown-menu .dropdown-item:not(.disabled)",A="top-start",b="top-end",D="bottom-start",S="bottom-end",w="right-start",N="left-start",O={offset:0,flip:!0,boundary:"scrollParent"},k={offset:"(number|string|function)",flip:"boolean",boundary:"(string|element)"},L=function(){function a(t,e){this._element=t,this._popper=null,this._config=this._getConfig(e),this._menu=this._getMenuElement(),this._inNavbar=this._detectNavbar(),this._addEventListeners()}var l=a.prototype;return l.toggle=function(){if(!this._element.disabled&&!t(this._element).hasClass(u)){var e=a._getParentFromElement(this._element),i=t(this._menu).hasClass(f);if(a._clearMenus(),!i){var s={relatedTarget:this._element},r=t.Event(c.SHOW,s);if(t(e).trigger(r),!r.isDefaultPrevented()){if(!this._inNavbar){if("undefined"==typeof n)throw new TypeError("Bootstrap dropdown require Popper.js (https://popper.js.org)");var o=this._element;t(e).hasClass(d)&&(t(this._menu).hasClass(m)||t(this._menu).hasClass(p))&&(o=e),"scrollParent"!==this._config.boundary&&t(e).addClass(v),this._popper=new n(o,this._menu,this._getPopperConfig())}"ontouchstart"in document.documentElement&&0===t(e).closest(C).length&&t("body").children().on("mouseover",null,t.noop),this._element.focus(),this._element.setAttribute("aria-expanded",!0),t(this._menu).toggleClass(f),t(e).toggleClass(f).trigger(t.Event(c.SHOWN,s))}}}},l.dispose=function(){t.removeData(this._element,i),t(this._element).off(o),this._element=null,this._menu=null,null!==this._popper&&(this._popper.destroy(),this._popper=null)},l.update=function(){this._inNavbar=this._detectNavbar(),null!==this._popper&&this._popper.scheduleUpdate()},l._addEventListeners=function(){var e=this;t(this._element).on(c.CLICK,function(t){t.preventDefault(),t.stopPropagation(),e.toggle()})},l._getConfig=function(n){return n=r({},this.constructor.Default,t(this._element).data(),n),P.typeCheckConfig(e,n,this.constructor.DefaultType),n},l._getMenuElement=function(){if(!this._menu){var e=a._getParentFromElement(this._element);this._menu=t(e).find(y)[0]}return this._menu},l._getPlacement=function(){var e=t(this._element).parent(),n=D;return e.hasClass(d)?(n=A,t(this._menu).hasClass(p)&&(n=b)):e.hasClass(_)?n=w:e.hasClass(g)?n=N:t(this._menu).hasClass(p)&&(n=S),n},l._detectNavbar=function(){return t(this._element).closest(".navbar").length>0},l._getPopperConfig=function(){var t=this,e={};return"function"==typeof this._config.offset?e.fn=function(e){return e.offsets=r({},e.offsets,t._config.offset(e.offsets)||{}),e}:e.offset=this._config.offset,{placement:this._getPlacement(),modifiers:{offset:e,flip:{enabled:this._config.flip},preventOverflow:{boundariesElement:this._config.boundary}}}},a._jQueryInterface=function(e){return this.each(function(){var n=t(this).data(i);if(n||(n=new a(this,"object"==typeof e?e:null),t(this).data(i,n)),"string"==typeof e){if("undefined"==typeof n[e])throw new TypeError('No method named "'+e+'"');n[e]()}})},a._clearMenus=function(e){if(!e||3!==e.which&&("keyup"!==e.type||9===e.which))for(var n=t.makeArray(t(E)),s=0;s0&&r--,40===e.which&&rdocument.documentElement.clientHeight;!this._isBodyOverflowing&&t&&(this._element.style.paddingLeft=this._scrollbarWidth+"px"),this._isBodyOverflowing&&!t&&(this._element.style.paddingRight=this._scrollbarWidth+"px")},p._resetAdjustments=function(){this._element.style.paddingLeft="",this._element.style.paddingRight=""},p._checkScrollbar=function(){var t=document.body.getBoundingClientRect();this._isBodyOverflowing=t.left+t.right',trigger:"hover focus",title:"",delay:0,html:!1,selector:!1,placement:"top",offset:0,container:!1,fallbackPlacement:"flip",boundary:"scrollParent"},f="show",d="out",_={HIDE:"hide"+o,HIDDEN:"hidden"+o,SHOW:"show"+o,SHOWN:"shown"+o,INSERTED:"inserted"+o,CLICK:"click"+o,FOCUSIN:"focusin"+o,FOCUSOUT:"focusout"+o,MOUSEENTER:"mouseenter"+o,MOUSELEAVE:"mouseleave"+o},g="fade",p="show",m=".tooltip-inner",v=".arrow",E="hover",T="focus",y="click",C="manual",I=function(){function a(t,e){if("undefined"==typeof n)throw new TypeError("Bootstrap tooltips require Popper.js (https://popper.js.org)");this._isEnabled=!0,this._timeout=0,this._hoverState="",this._activeTrigger={},this._popper=null,this.element=t,this.config=this._getConfig(e),this.tip=null,this._setListeners()}var I=a.prototype;return I.enable=function(){this._isEnabled=!0},I.disable=function(){this._isEnabled=!1},I.toggleEnabled=function(){this._isEnabled=!this._isEnabled},I.toggle=function(e){if(this._isEnabled)if(e){var n=this.constructor.DATA_KEY,i=t(e.currentTarget).data(n);i||(i=new this.constructor(e.currentTarget,this._getDelegateConfig()),t(e.currentTarget).data(n,i)),i._activeTrigger.click=!i._activeTrigger.click,i._isWithActiveTrigger()?i._enter(null,i):i._leave(null,i)}else{if(t(this.getTipElement()).hasClass(p))return void this._leave(null,this);this._enter(null,this)}},I.dispose=function(){clearTimeout(this._timeout),t.removeData(this.element,this.constructor.DATA_KEY),t(this.element).off(this.constructor.EVENT_KEY),t(this.element).closest(".modal").off("hide.bs.modal"),this.tip&&t(this.tip).remove(),this._isEnabled=null,this._timeout=null,this._hoverState=null,this._activeTrigger=null,null!==this._popper&&this._popper.destroy(),this._popper=null,this.element=null,this.config=null,this.tip=null},I.show=function(){var e=this;if("none"===t(this.element).css("display"))throw new Error("Please use show on visible elements");var i=t.Event(this.constructor.Event.SHOW);if(this.isWithContent()&&this._isEnabled){t(this.element).trigger(i);var s=t.contains(this.element.ownerDocument.documentElement,this.element);if(i.isDefaultPrevented()||!s)return;var r=this.getTipElement(),o=P.getUID(this.constructor.NAME);r.setAttribute("id",o),this.element.setAttribute("aria-describedby",o),this.setContent(),this.config.animation&&t(r).addClass(g);var l="function"==typeof this.config.placement?this.config.placement.call(this,r,this.element):this.config.placement,h=this._getAttachment(l);this.addAttachmentClass(h);var c=!1===this.config.container?document.body:t(this.config.container);t(r).data(this.constructor.DATA_KEY,this),t.contains(this.element.ownerDocument.documentElement,this.tip)||t(r).appendTo(c),t(this.element).trigger(this.constructor.Event.INSERTED),this._popper=new n(this.element,r,{placement:h,modifiers:{offset:{offset:this.config.offset},flip:{behavior:this.config.fallbackPlacement},arrow:{element:v},preventOverflow:{boundariesElement:this.config.boundary}},onCreate:function(t){t.originalPlacement!==t.placement&&e._handlePopperPlacementChange(t)},onUpdate:function(t){e._handlePopperPlacementChange(t)}}),t(r).addClass(p),"ontouchstart"in document.documentElement&&t("body").children().on("mouseover",null,t.noop);var u=function(){e.config.animation&&e._fixTransition();var n=e._hoverState;e._hoverState=null,t(e.element).trigger(e.constructor.Event.SHOWN),n===d&&e._leave(null,e)};P.supportsTransitionEnd()&&t(this.tip).hasClass(g)?t(this.tip).one(P.TRANSITION_END,u).emulateTransitionEnd(a._TRANSITION_DURATION):u()}},I.hide=function(e){var n=this,i=this.getTipElement(),s=t.Event(this.constructor.Event.HIDE),r=function(){n._hoverState!==f&&i.parentNode&&i.parentNode.removeChild(i),n._cleanTipClass(),n.element.removeAttribute("aria-describedby"),t(n.element).trigger(n.constructor.Event.HIDDEN),null!==n._popper&&n._popper.destroy(),e&&e()};t(this.element).trigger(s),s.isDefaultPrevented()||(t(i).removeClass(p),"ontouchstart"in document.documentElement&&t("body").children().off("mouseover",null,t.noop),this._activeTrigger[y]=!1,this._activeTrigger[T]=!1,this._activeTrigger[E]=!1,P.supportsTransitionEnd()&&t(this.tip).hasClass(g)?t(i).one(P.TRANSITION_END,r).emulateTransitionEnd(150):r(),this._hoverState="")},I.update=function(){null!==this._popper&&this._popper.scheduleUpdate()},I.isWithContent=function(){return Boolean(this.getTitle())},I.addAttachmentClass=function(e){t(this.getTipElement()).addClass("bs-tooltip-"+e)},I.getTipElement=function(){return this.tip=this.tip||t(this.config.template)[0],this.tip},I.setContent=function(){var e=t(this.getTipElement());this.setElementContent(e.find(m),this.getTitle()),e.removeClass(g+" "+p)},I.setElementContent=function(e,n){var i=this.config.html;"object"==typeof n&&(n.nodeType||n.jquery)?i?t(n).parent().is(e)||e.empty().append(n):e.text(t(n).text()):e[i?"html":"text"](n)},I.getTitle=function(){var t=this.element.getAttribute("data-original-title");return t||(t="function"==typeof this.config.title?this.config.title.call(this.element):this.config.title),t},I._getAttachment=function(t){return c[t.toUpperCase()]},I._setListeners=function(){var e=this;this.config.trigger.split(" ").forEach(function(n){if("click"===n)t(e.element).on(e.constructor.Event.CLICK,e.config.selector,function(t){return e.toggle(t)});else if(n!==C){var i=n===E?e.constructor.Event.MOUSEENTER:e.constructor.Event.FOCUSIN,s=n===E?e.constructor.Event.MOUSELEAVE:e.constructor.Event.FOCUSOUT;t(e.element).on(i,e.config.selector,function(t){return e._enter(t)}).on(s,e.config.selector,function(t){return e._leave(t)})}t(e.element).closest(".modal").on("hide.bs.modal",function(){return e.hide()})}),this.config.selector?this.config=r({},this.config,{trigger:"manual",selector:""}):this._fixTitle()},I._fixTitle=function(){var t=typeof this.element.getAttribute("data-original-title");(this.element.getAttribute("title")||"string"!==t)&&(this.element.setAttribute("data-original-title",this.element.getAttribute("title")||""),this.element.setAttribute("title",""))},I._enter=function(e,n){var i=this.constructor.DATA_KEY;(n=n||t(e.currentTarget).data(i))||(n=new this.constructor(e.currentTarget,this._getDelegateConfig()),t(e.currentTarget).data(i,n)),e&&(n._activeTrigger["focusin"===e.type?T:E]=!0),t(n.getTipElement()).hasClass(p)||n._hoverState===f?n._hoverState=f:(clearTimeout(n._timeout),n._hoverState=f,n.config.delay&&n.config.delay.show?n._timeout=setTimeout(function(){n._hoverState===f&&n.show()},n.config.delay.show):n.show())},I._leave=function(e,n){var i=this.constructor.DATA_KEY;(n=n||t(e.currentTarget).data(i))||(n=new this.constructor(e.currentTarget,this._getDelegateConfig()),t(e.currentTarget).data(i,n)),e&&(n._activeTrigger["focusout"===e.type?T:E]=!1),n._isWithActiveTrigger()||(clearTimeout(n._timeout),n._hoverState=d,n.config.delay&&n.config.delay.hide?n._timeout=setTimeout(function(){n._hoverState===d&&n.hide()},n.config.delay.hide):n.hide())},I._isWithActiveTrigger=function(){for(var t in this._activeTrigger)if(this._activeTrigger[t])return!0;return!1},I._getConfig=function(n){return"number"==typeof(n=r({},this.constructor.Default,t(this.element).data(),n)).delay&&(n.delay={show:n.delay,hide:n.delay}),"number"==typeof n.title&&(n.title=n.title.toString()),"number"==typeof n.content&&(n.content=n.content.toString()),P.typeCheckConfig(e,n,this.constructor.DefaultType),n},I._getDelegateConfig=function(){var t={};if(this.config)for(var e in this.config)this.constructor.Default[e]!==this.config[e]&&(t[e]=this.config[e]);return t},I._cleanTipClass=function(){var e=t(this.getTipElement()),n=e.attr("class").match(l);null!==n&&n.length>0&&e.removeClass(n.join(""))},I._handlePopperPlacementChange=function(t){this._cleanTipClass(),this.addAttachmentClass(this._getAttachment(t.placement))},I._fixTransition=function(){var e=this.getTipElement(),n=this.config.animation;null===e.getAttribute("x-placement")&&(t(e).removeClass(g),this.config.animation=!1,this.hide(),this.show(),this.config.animation=n)},a._jQueryInterface=function(e){return this.each(function(){var n=t(this).data(i),s="object"==typeof e&&e;if((n||!/dispose|hide/.test(e))&&(n||(n=new a(this,s),t(this).data(i,n)),"string"==typeof e)){if("undefined"==typeof n[e])throw new TypeError('No method named "'+e+'"');n[e]()}})},s(a,null,[{key:"VERSION",get:function(){return"4.0.0"}},{key:"Default",get:function(){return u}},{key:"NAME",get:function(){return e}},{key:"DATA_KEY",get:function(){return i}},{key:"Event",get:function(){return _}},{key:"EVENT_KEY",get:function(){return o}},{key:"DefaultType",get:function(){return h}}]),a}();return t.fn[e]=I._jQueryInterface,t.fn[e].Constructor=I,t.fn[e].noConflict=function(){return t.fn[e]=a,I._jQueryInterface},I}(e),x=function(t){var e="popover",n="bs.popover",i="."+n,o=t.fn[e],a=new RegExp("(^|\\s)bs-popover\\S+","g"),l=r({},U.Default,{placement:"right",trigger:"click",content:"",template:''}),h=r({},U.DefaultType,{content:"(string|element|function)"}),c="fade",u="show",f=".popover-header",d=".popover-body",_={HIDE:"hide"+i,HIDDEN:"hidden"+i,SHOW:"show"+i,SHOWN:"shown"+i,INSERTED:"inserted"+i,CLICK:"click"+i,FOCUSIN:"focusin"+i,FOCUSOUT:"focusout"+i,MOUSEENTER:"mouseenter"+i,MOUSELEAVE:"mouseleave"+i},g=function(r){var o,g;function p(){return r.apply(this,arguments)||this}g=r,(o=p).prototype=Object.create(g.prototype),o.prototype.constructor=o,o.__proto__=g;var m=p.prototype;return m.isWithContent=function(){return this.getTitle()||this._getContent()},m.addAttachmentClass=function(e){t(this.getTipElement()).addClass("bs-popover-"+e)},m.getTipElement=function(){return this.tip=this.tip||t(this.config.template)[0],this.tip},m.setContent=function(){var e=t(this.getTipElement());this.setElementContent(e.find(f),this.getTitle());var n=this._getContent();"function"==typeof n&&(n=n.call(this.element)),this.setElementContent(e.find(d),n),e.removeClass(c+" "+u)},m._getContent=function(){return this.element.getAttribute("data-content")||this.config.content},m._cleanTipClass=function(){var e=t(this.getTipElement()),n=e.attr("class").match(a);null!==n&&n.length>0&&e.removeClass(n.join(""))},p._jQueryInterface=function(e){return this.each(function(){var i=t(this).data(n),s="object"==typeof e?e:null;if((i||!/destroy|hide/.test(e))&&(i||(i=new p(this,s),t(this).data(n,i)),"string"==typeof e)){if("undefined"==typeof i[e])throw new TypeError('No method named "'+e+'"');i[e]()}})},s(p,null,[{key:"VERSION",get:function(){return"4.0.0"}},{key:"Default",get:function(){return l}},{key:"NAME",get:function(){return e}},{key:"DATA_KEY",get:function(){return n}},{key:"Event",get:function(){return _}},{key:"EVENT_KEY",get:function(){return i}},{key:"DefaultType",get:function(){return h}}]),p}(U);return t.fn[e]=g._jQueryInterface,t.fn[e].Constructor=g,t.fn[e].noConflict=function(){return t.fn[e]=o,g._jQueryInterface},g}(e),K=function(t){var e="scrollspy",n="bs.scrollspy",i="."+n,o=t.fn[e],a={offset:10,method:"auto",target:""},l={offset:"number",method:"string",target:"(string|element)"},h={ACTIVATE:"activate"+i,SCROLL:"scroll"+i,LOAD_DATA_API:"load"+i+".data-api"},c="dropdown-item",u="active",f={DATA_SPY:'[data-spy="scroll"]',ACTIVE:".active",NAV_LIST_GROUP:".nav, .list-group",NAV_LINKS:".nav-link",NAV_ITEMS:".nav-item",LIST_ITEMS:".list-group-item",DROPDOWN:".dropdown",DROPDOWN_ITEMS:".dropdown-item",DROPDOWN_TOGGLE:".dropdown-toggle"},d="offset",_="position",g=function(){function o(e,n){var i=this;this._element=e,this._scrollElement="BODY"===e.tagName?window:e,this._config=this._getConfig(n),this._selector=this._config.target+" "+f.NAV_LINKS+","+this._config.target+" "+f.LIST_ITEMS+","+this._config.target+" "+f.DROPDOWN_ITEMS,this._offsets=[],this._targets=[],this._activeTarget=null,this._scrollHeight=0,t(this._scrollElement).on(h.SCROLL,function(t){return i._process(t)}),this.refresh(),this._process()}var g=o.prototype;return g.refresh=function(){var e=this,n=this._scrollElement===this._scrollElement.window?d:_,i="auto"===this._config.method?n:this._config.method,s=i===_?this._getScrollTop():0;this._offsets=[],this._targets=[],this._scrollHeight=this._getScrollHeight(),t.makeArray(t(this._selector)).map(function(e){var n,r=P.getSelectorFromElement(e);if(r&&(n=t(r)[0]),n){var o=n.getBoundingClientRect();if(o.width||o.height)return[t(n)[i]().top+s,r]}return null}).filter(function(t){return t}).sort(function(t,e){return t[0]-e[0]}).forEach(function(t){e._offsets.push(t[0]),e._targets.push(t[1])})},g.dispose=function(){t.removeData(this._element,n),t(this._scrollElement).off(i),this._element=null,this._scrollElement=null,this._config=null,this._selector=null,this._offsets=null,this._targets=null,this._activeTarget=null,this._scrollHeight=null},g._getConfig=function(n){if("string"!=typeof(n=r({},a,n)).target){var i=t(n.target).attr("id");i||(i=P.getUID(e),t(n.target).attr("id",i)),n.target="#"+i}return P.typeCheckConfig(e,n,l),n},g._getScrollTop=function(){return this._scrollElement===window?this._scrollElement.pageYOffset:this._scrollElement.scrollTop},g._getScrollHeight=function(){return this._scrollElement.scrollHeight||Math.max(document.body.scrollHeight,document.documentElement.scrollHeight)},g._getOffsetHeight=function(){return this._scrollElement===window?window.innerHeight:this._scrollElement.getBoundingClientRect().height},g._process=function(){var t=this._getScrollTop()+this._config.offset,e=this._getScrollHeight(),n=this._config.offset+e-this._getOffsetHeight();if(this._scrollHeight!==e&&this.refresh(),t>=n){var i=this._targets[this._targets.length-1];this._activeTarget!==i&&this._activate(i)}else{if(this._activeTarget&&t0)return this._activeTarget=null,void this._clear();for(var s=this._offsets.length;s--;){this._activeTarget!==this._targets[s]&&t>=this._offsets[s]&&("undefined"==typeof this._offsets[s+1]||t li > .active",g='[data-toggle="tab"], [data-toggle="pill"], [data-toggle="list"]',p=".dropdown-toggle",m="> .dropdown-menu .active",v=function(){function n(t){this._element=t}var i=n.prototype;return i.show=function(){var e=this;if(!(this._element.parentNode&&this._element.parentNode.nodeType===Node.ELEMENT_NODE&&t(this._element).hasClass(a)||t(this._element).hasClass(l))){var n,i,s=t(this._element).closest(f)[0],o=P.getSelectorFromElement(this._element);if(s){var h="UL"===s.nodeName?_:d;i=(i=t.makeArray(t(s).find(h)))[i.length-1]}var c=t.Event(r.HIDE,{relatedTarget:this._element}),u=t.Event(r.SHOW,{relatedTarget:i});if(i&&t(i).trigger(c),t(this._element).trigger(u),!u.isDefaultPrevented()&&!c.isDefaultPrevented()){o&&(n=t(o)[0]),this._activate(this._element,s);var g=function(){var n=t.Event(r.HIDDEN,{relatedTarget:e._element}),s=t.Event(r.SHOWN,{relatedTarget:i});t(i).trigger(n),t(e._element).trigger(s)};n?this._activate(n,n.parentNode,g):g()}}},i.dispose=function(){t.removeData(this._element,e),this._element=null},i._activate=function(e,n,i){var s=this,r=("UL"===n.nodeName?t(n).find(_):t(n).children(d))[0],o=i&&P.supportsTransitionEnd()&&r&&t(r).hasClass(h),a=function(){return s._transitionComplete(e,r,i)};r&&o?t(r).one(P.TRANSITION_END,a).emulateTransitionEnd(150):a()},i._transitionComplete=function(e,n,i){if(n){t(n).removeClass(c+" "+a);var s=t(n.parentNode).find(m)[0];s&&t(s).removeClass(a),"tab"===n.getAttribute("role")&&n.setAttribute("aria-selected",!1)}if(t(e).addClass(a),"tab"===e.getAttribute("role")&&e.setAttribute("aria-selected",!0),P.reflow(e),t(e).addClass(c),e.parentNode&&t(e.parentNode).hasClass(o)){var r=t(e).closest(u)[0];r&&t(r).find(p).addClass(a),e.setAttribute("aria-expanded",!0)}i&&i()},n._jQueryInterface=function(i){return this.each(function(){var s=t(this),r=s.data(e);if(r||(r=new n(this),s.data(e,r)),"string"==typeof i){if("undefined"==typeof r[i])throw new TypeError('No method named "'+i+'"');r[i]()}})},s(n,null,[{key:"VERSION",get:function(){return"4.0.0"}}]),n}();return t(document).on(r.CLICK_DATA_API,g,function(e){e.preventDefault(),v._jQueryInterface.call(t(this),"show")}),t.fn.tab=v._jQueryInterface,t.fn.tab.Constructor=v,t.fn.tab.noConflict=function(){return t.fn.tab=i,v._jQueryInterface},v}(e);!function(t){if("undefined"==typeof t)throw new TypeError("Bootstrap's JavaScript requires jQuery. jQuery must be included before Bootstrap's JavaScript.");var e=t.fn.jquery.split(" ")[0].split(".");if(e[0]<2&&e[1]<9||1===e[0]&&9===e[1]&&e[2]<1||e[0]>=4)throw new Error("Bootstrap's JavaScript requires at least jQuery v1.9.1 but less than v4.0.0")}(e),t.Util=P,t.Alert=L,t.Button=R,t.Carousel=j,t.Collapse=H,t.Dropdown=W,t.Modal=M,t.Popover=x,t.Scrollspy=K,t.Tab=V,t.Tooltip=U,Object.defineProperty(t,"__esModule",{value:!0})});
7 | //# sourceMappingURL=bootstrap.min.js.map
--------------------------------------------------------------------------------
/reactjs/public/js/dataTables.bootstrap4.min.js:
--------------------------------------------------------------------------------
1 | /*!
2 | DataTables Bootstrap 4 integration
3 | ©2011-2017 SpryMedia Ltd - datatables.net/license
4 | */
5 | (function(b){"function"===typeof define&&define.amd?define(["jquery","datatables.net"],function(a){return b(a,window,document)}):"object"===typeof exports?module.exports=function(a,d){a||(a=window);if(!d||!d.fn.dataTable)d=require("datatables.net")(a,d).$;return b(d,a,a.document)}:b(jQuery,window,document)})(function(b,a,d,m){var f=b.fn.dataTable;b.extend(!0,f.defaults,{dom:"<'row'<'col-sm-12 col-md-6'l><'col-sm-12 col-md-6'f>><'row'<'col-sm-12'tr>><'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>",
6 | renderer:"bootstrap"});b.extend(f.ext.classes,{sWrapper:"dataTables_wrapper dt-bootstrap4",sFilterInput:"form-control form-control-sm",sLengthSelect:"custom-select custom-select-sm form-control form-control-sm",sProcessing:"dataTables_processing card",sPageButton:"paginate_button page-item"});f.ext.renderer.pageButton.bootstrap=function(a,h,r,s,j,n){var o=new f.Api(a),t=a.oClasses,k=a.oLanguage.oPaginate,u=a.oLanguage.oAria.paginate||{},e,g,p=0,q=function(d,f){var l,h,i,c,m=function(a){a.preventDefault();
7 | !b(a.currentTarget).hasClass("disabled")&&o.page()!=a.data.action&&o.page(a.data.action).draw("page")};l=0;for(h=f.length;l",
8 | {"class":t.sPageButton+" "+g,id:0===r&&"string"===typeof c?a.sTableId+"_"+c:null}).append(b("",{href:"#","aria-controls":a.sTableId,"aria-label":u[c],"data-dt-idx":p,tabindex:a.iTabIndex,"class":"page-link"}).html(e)).appendTo(d),a.oApi._fnBindAction(i,{action:c},m),p++)}},i;try{i=b(h).find(d.activeElement).data("dt-idx")}catch(v){}q(b(h).empty().html('').children("ul"),s);i!==m&&b(h).find("[data-dt-idx="+i+"]").focus()};return f});
9 |
--------------------------------------------------------------------------------
/reactjs/public/js/jquery.validate.min.js:
--------------------------------------------------------------------------------
1 | /*! jQuery Validation Plugin - v1.17.0 - 7/29/2017
2 | * https://jqueryvalidation.org/
3 | * Copyright (c) 2017 Jörn Zaefferer; Licensed MIT */
4 | !function(a){"function"==typeof define&&define.amd?define(["jquery"],a):"object"==typeof module&&module.exports?module.exports=a(require("jquery")):a(jQuery)}(function(a){a.extend(a.fn,{validate:function(b){if(!this.length)return void(b&&b.debug&&window.console&&console.warn("Nothing selected, can't validate, returning nothing."));var c=a.data(this[0],"validator");return c?c:(this.attr("novalidate","novalidate"),c=new a.validator(b,this[0]),a.data(this[0],"validator",c),c.settings.onsubmit&&(this.on("click.validate",":submit",function(b){c.submitButton=b.currentTarget,a(this).hasClass("cancel")&&(c.cancelSubmit=!0),void 0!==a(this).attr("formnovalidate")&&(c.cancelSubmit=!0)}),this.on("submit.validate",function(b){function d(){var d,e;return c.submitButton&&(c.settings.submitHandler||c.formSubmitted)&&(d=a("").attr("name",c.submitButton.name).val(a(c.submitButton).val()).appendTo(c.currentForm)),!c.settings.submitHandler||(e=c.settings.submitHandler.call(c,c.currentForm,b),d&&d.remove(),void 0!==e&&e)}return c.settings.debug&&b.preventDefault(),c.cancelSubmit?(c.cancelSubmit=!1,d()):c.form()?c.pendingRequest?(c.formSubmitted=!0,!1):d():(c.focusInvalid(),!1)})),c)},valid:function(){var b,c,d;return a(this[0]).is("form")?b=this.validate().form():(d=[],b=!0,c=a(this[0].form).validate(),this.each(function(){b=c.element(this)&&b,b||(d=d.concat(c.errorList))}),c.errorList=d),b},rules:function(b,c){var d,e,f,g,h,i,j=this[0];if(null!=j&&(!j.form&&j.hasAttribute("contenteditable")&&(j.form=this.closest("form")[0],j.name=this.attr("name")),null!=j.form)){if(b)switch(d=a.data(j.form,"validator").settings,e=d.rules,f=a.validator.staticRules(j),b){case"add":a.extend(f,a.validator.normalizeRule(c)),delete f.messages,e[j.name]=f,c.messages&&(d.messages[j.name]=a.extend(d.messages[j.name],c.messages));break;case"remove":return c?(i={},a.each(c.split(/\s/),function(a,b){i[b]=f[b],delete f[b]}),i):(delete e[j.name],f)}return g=a.validator.normalizeRules(a.extend({},a.validator.classRules(j),a.validator.attributeRules(j),a.validator.dataRules(j),a.validator.staticRules(j)),j),g.required&&(h=g.required,delete g.required,g=a.extend({required:h},g)),g.remote&&(h=g.remote,delete g.remote,g=a.extend(g,{remote:h})),g}}}),a.extend(a.expr.pseudos||a.expr[":"],{blank:function(b){return!a.trim(""+a(b).val())},filled:function(b){var c=a(b).val();return null!==c&&!!a.trim(""+c)},unchecked:function(b){return!a(b).prop("checked")}}),a.validator=function(b,c){this.settings=a.extend(!0,{},a.validator.defaults,b),this.currentForm=c,this.init()},a.validator.format=function(b,c){return 1===arguments.length?function(){var c=a.makeArray(arguments);return c.unshift(b),a.validator.format.apply(this,c)}:void 0===c?b:(arguments.length>2&&c.constructor!==Array&&(c=a.makeArray(arguments).slice(1)),c.constructor!==Array&&(c=[c]),a.each(c,function(a,c){b=b.replace(new RegExp("\\{"+a+"\\}","g"),function(){return c})}),b)},a.extend(a.validator,{defaults:{messages:{},groups:{},rules:{},errorClass:"error",pendingClass:"pending",validClass:"valid",errorElement:"label",focusCleanup:!1,focusInvalid:!0,errorContainer:a([]),errorLabelContainer:a([]),onsubmit:!0,ignore:":hidden",ignoreTitle:!1,onfocusin:function(a){this.lastActive=a,this.settings.focusCleanup&&(this.settings.unhighlight&&this.settings.unhighlight.call(this,a,this.settings.errorClass,this.settings.validClass),this.hideThese(this.errorsFor(a)))},onfocusout:function(a){this.checkable(a)||!(a.name in this.submitted)&&this.optional(a)||this.element(a)},onkeyup:function(b,c){var d=[16,17,18,20,35,36,37,38,39,40,45,144,225];9===c.which&&""===this.elementValue(b)||a.inArray(c.keyCode,d)!==-1||(b.name in this.submitted||b.name in this.invalid)&&this.element(b)},onclick:function(a){a.name in this.submitted?this.element(a):a.parentNode.name in this.submitted&&this.element(a.parentNode)},highlight:function(b,c,d){"radio"===b.type?this.findByName(b.name).addClass(c).removeClass(d):a(b).addClass(c).removeClass(d)},unhighlight:function(b,c,d){"radio"===b.type?this.findByName(b.name).removeClass(c).addClass(d):a(b).removeClass(c).addClass(d)}},setDefaults:function(b){a.extend(a.validator.defaults,b)},messages:{required:"This field is required.",remote:"Please fix this field.",email:"Please enter a valid email address.",url:"Please enter a valid URL.",date:"Please enter a valid date.",dateISO:"Please enter a valid date (ISO).",number:"Please enter a valid number.",digits:"Please enter only digits.",equalTo:"Please enter the same value again.",maxlength:a.validator.format("Please enter no more than {0} characters."),minlength:a.validator.format("Please enter at least {0} characters."),rangelength:a.validator.format("Please enter a value between {0} and {1} characters long."),range:a.validator.format("Please enter a value between {0} and {1}."),max:a.validator.format("Please enter a value less than or equal to {0}."),min:a.validator.format("Please enter a value greater than or equal to {0}."),step:a.validator.format("Please enter a multiple of {0}.")},autoCreateRanges:!1,prototype:{init:function(){function b(b){!this.form&&this.hasAttribute("contenteditable")&&(this.form=a(this).closest("form")[0],this.name=a(this).attr("name"));var c=a.data(this.form,"validator"),d="on"+b.type.replace(/^validate/,""),e=c.settings;e[d]&&!a(this).is(e.ignore)&&e[d].call(c,this,b)}this.labelContainer=a(this.settings.errorLabelContainer),this.errorContext=this.labelContainer.length&&this.labelContainer||a(this.currentForm),this.containers=a(this.settings.errorContainer).add(this.settings.errorLabelContainer),this.submitted={},this.valueCache={},this.pendingRequest=0,this.pending={},this.invalid={},this.reset();var c,d=this.groups={};a.each(this.settings.groups,function(b,c){"string"==typeof c&&(c=c.split(/\s/)),a.each(c,function(a,c){d[c]=b})}),c=this.settings.rules,a.each(c,function(b,d){c[b]=a.validator.normalizeRule(d)}),a(this.currentForm).on("focusin.validate focusout.validate keyup.validate",":text, [type='password'], [type='file'], select, textarea, [type='number'], [type='search'], [type='tel'], [type='url'], [type='email'], [type='datetime'], [type='date'], [type='month'], [type='week'], [type='time'], [type='datetime-local'], [type='range'], [type='color'], [type='radio'], [type='checkbox'], [contenteditable], [type='button']",b).on("click.validate","select, option, [type='radio'], [type='checkbox']",b),this.settings.invalidHandler&&a(this.currentForm).on("invalid-form.validate",this.settings.invalidHandler)},form:function(){return this.checkForm(),a.extend(this.submitted,this.errorMap),this.invalid=a.extend({},this.errorMap),this.valid()||a(this.currentForm).triggerHandler("invalid-form",[this]),this.showErrors(),this.valid()},checkForm:function(){this.prepareForm();for(var a=0,b=this.currentElements=this.elements();b[a];a++)this.check(b[a]);return this.valid()},element:function(b){var c,d,e=this.clean(b),f=this.validationTargetFor(e),g=this,h=!0;return void 0===f?delete this.invalid[e.name]:(this.prepareElement(f),this.currentElements=a(f),d=this.groups[f.name],d&&a.each(this.groups,function(a,b){b===d&&a!==f.name&&(e=g.validationTargetFor(g.clean(g.findByName(a))),e&&e.name in g.invalid&&(g.currentElements.push(e),h=g.check(e)&&h))}),c=this.check(f)!==!1,h=h&&c,c?this.invalid[f.name]=!1:this.invalid[f.name]=!0,this.numberOfInvalids()||(this.toHide=this.toHide.add(this.containers)),this.showErrors(),a(b).attr("aria-invalid",!c)),h},showErrors:function(b){if(b){var c=this;a.extend(this.errorMap,b),this.errorList=a.map(this.errorMap,function(a,b){return{message:a,element:c.findByName(b)[0]}}),this.successList=a.grep(this.successList,function(a){return!(a.name in b)})}this.settings.showErrors?this.settings.showErrors.call(this,this.errorMap,this.errorList):this.defaultShowErrors()},resetForm:function(){a.fn.resetForm&&a(this.currentForm).resetForm(),this.invalid={},this.submitted={},this.prepareForm(),this.hideErrors();var b=this.elements().removeData("previousValue").removeAttr("aria-invalid");this.resetElements(b)},resetElements:function(a){var b;if(this.settings.unhighlight)for(b=0;a[b];b++)this.settings.unhighlight.call(this,a[b],this.settings.errorClass,""),this.findByName(a[b].name).removeClass(this.settings.validClass);else a.removeClass(this.settings.errorClass).removeClass(this.settings.validClass)},numberOfInvalids:function(){return this.objectLength(this.invalid)},objectLength:function(a){var b,c=0;for(b in a)void 0!==a[b]&&null!==a[b]&&a[b]!==!1&&c++;return c},hideErrors:function(){this.hideThese(this.toHide)},hideThese:function(a){a.not(this.containers).text(""),this.addWrapper(a).hide()},valid:function(){return 0===this.size()},size:function(){return this.errorList.length},focusInvalid:function(){if(this.settings.focusInvalid)try{a(this.findLastActive()||this.errorList.length&&this.errorList[0].element||[]).filter(":visible").focus().trigger("focusin")}catch(b){}},findLastActive:function(){var b=this.lastActive;return b&&1===a.grep(this.errorList,function(a){return a.element.name===b.name}).length&&b},elements:function(){var b=this,c={};return a(this.currentForm).find("input, select, textarea, [contenteditable]").not(":submit, :reset, :image, :disabled").not(this.settings.ignore).filter(function(){var d=this.name||a(this).attr("name");return!d&&b.settings.debug&&window.console&&console.error("%o has no name assigned",this),this.hasAttribute("contenteditable")&&(this.form=a(this).closest("form")[0],this.name=d),!(d in c||!b.objectLength(a(this).rules()))&&(c[d]=!0,!0)})},clean:function(b){return a(b)[0]},errors:function(){var b=this.settings.errorClass.split(" ").join(".");return a(this.settings.errorElement+"."+b,this.errorContext)},resetInternals:function(){this.successList=[],this.errorList=[],this.errorMap={},this.toShow=a([]),this.toHide=a([])},reset:function(){this.resetInternals(),this.currentElements=a([])},prepareForm:function(){this.reset(),this.toHide=this.errors().add(this.containers)},prepareElement:function(a){this.reset(),this.toHide=this.errorsFor(a)},elementValue:function(b){var c,d,e=a(b),f=b.type;return"radio"===f||"checkbox"===f?this.findByName(b.name).filter(":checked").val():"number"===f&&"undefined"!=typeof b.validity?b.validity.badInput?"NaN":e.val():(c=b.hasAttribute("contenteditable")?e.text():e.val(),"file"===f?"C:\\fakepath\\"===c.substr(0,12)?c.substr(12):(d=c.lastIndexOf("/"),d>=0?c.substr(d+1):(d=c.lastIndexOf("\\"),d>=0?c.substr(d+1):c)):"string"==typeof c?c.replace(/\r/g,""):c)},check:function(b){b=this.validationTargetFor(this.clean(b));var c,d,e,f,g=a(b).rules(),h=a.map(g,function(a,b){return b}).length,i=!1,j=this.elementValue(b);if("function"==typeof g.normalizer?f=g.normalizer:"function"==typeof this.settings.normalizer&&(f=this.settings.normalizer),f){if(j=f.call(b,j),"string"!=typeof j)throw new TypeError("The normalizer should return a string value.");delete g.normalizer}for(d in g){e={method:d,parameters:g[d]};try{if(c=a.validator.methods[d].call(this,j,b,e.parameters),"dependency-mismatch"===c&&1===h){i=!0;continue}if(i=!1,"pending"===c)return void(this.toHide=this.toHide.not(this.errorsFor(b)));if(!c)return this.formatAndAdd(b,e),!1}catch(k){throw this.settings.debug&&window.console&&console.log("Exception occurred when checking element "+b.id+", check the '"+e.method+"' method.",k),k instanceof TypeError&&(k.message+=". Exception occurred when checking element "+b.id+", check the '"+e.method+"' method."),k}}if(!i)return this.objectLength(g)&&this.successList.push(b),!0},customDataMessage:function(b,c){return a(b).data("msg"+c.charAt(0).toUpperCase()+c.substring(1).toLowerCase())||a(b).data("msg")},customMessage:function(a,b){var c=this.settings.messages[a];return c&&(c.constructor===String?c:c[b])},findDefined:function(){for(var a=0;aWarning: No message defined for "+b.name+""),e=/\$?\{(\d+)\}/g;return"function"==typeof d?d=d.call(this,c.parameters,b):e.test(d)&&(d=a.validator.format(d.replace(e,"{$1}"),c.parameters)),d},formatAndAdd:function(a,b){var c=this.defaultMessage(a,b);this.errorList.push({message:c,element:a,method:b.method}),this.errorMap[a.name]=c,this.submitted[a.name]=c},addWrapper:function(a){return this.settings.wrapper&&(a=a.add(a.parent(this.settings.wrapper))),a},defaultShowErrors:function(){var a,b,c;for(a=0;this.errorList[a];a++)c=this.errorList[a],this.settings.highlight&&this.settings.highlight.call(this,c.element,this.settings.errorClass,this.settings.validClass),this.showLabel(c.element,c.message);if(this.errorList.length&&(this.toShow=this.toShow.add(this.containers)),this.settings.success)for(a=0;this.successList[a];a++)this.showLabel(this.successList[a]);if(this.settings.unhighlight)for(a=0,b=this.validElements();b[a];a++)this.settings.unhighlight.call(this,b[a],this.settings.errorClass,this.settings.validClass);this.toHide=this.toHide.not(this.toShow),this.hideErrors(),this.addWrapper(this.toShow).show()},validElements:function(){return this.currentElements.not(this.invalidElements())},invalidElements:function(){return a(this.errorList).map(function(){return this.element})},showLabel:function(b,c){var d,e,f,g,h=this.errorsFor(b),i=this.idOrName(b),j=a(b).attr("aria-describedby");h.length?(h.removeClass(this.settings.validClass).addClass(this.settings.errorClass),h.html(c)):(h=a("<"+this.settings.errorElement+">").attr("id",i+"-error").addClass(this.settings.errorClass).html(c||""),d=h,this.settings.wrapper&&(d=h.hide().show().wrap("<"+this.settings.wrapper+"/>").parent()),this.labelContainer.length?this.labelContainer.append(d):this.settings.errorPlacement?this.settings.errorPlacement.call(this,d,a(b)):d.insertAfter(b),h.is("label")?h.attr("for",i):0===h.parents("label[for='"+this.escapeCssMeta(i)+"']").length&&(f=h.attr("id"),j?j.match(new RegExp("\\b"+this.escapeCssMeta(f)+"\\b"))||(j+=" "+f):j=f,a(b).attr("aria-describedby",j),e=this.groups[b.name],e&&(g=this,a.each(g.groups,function(b,c){c===e&&a("[name='"+g.escapeCssMeta(b)+"']",g.currentForm).attr("aria-describedby",h.attr("id"))})))),!c&&this.settings.success&&(h.text(""),"string"==typeof this.settings.success?h.addClass(this.settings.success):this.settings.success(h,b)),this.toShow=this.toShow.add(h)},errorsFor:function(b){var c=this.escapeCssMeta(this.idOrName(b)),d=a(b).attr("aria-describedby"),e="label[for='"+c+"'], label[for='"+c+"'] *";return d&&(e=e+", #"+this.escapeCssMeta(d).replace(/\s+/g,", #")),this.errors().filter(e)},escapeCssMeta:function(a){return a.replace(/([\\!"#$%&'()*+,.\/:;<=>?@\[\]^`{|}~])/g,"\\$1")},idOrName:function(a){return this.groups[a.name]||(this.checkable(a)?a.name:a.id||a.name)},validationTargetFor:function(b){return this.checkable(b)&&(b=this.findByName(b.name)),a(b).not(this.settings.ignore)[0]},checkable:function(a){return/radio|checkbox/i.test(a.type)},findByName:function(b){return a(this.currentForm).find("[name='"+this.escapeCssMeta(b)+"']")},getLength:function(b,c){switch(c.nodeName.toLowerCase()){case"select":return a("option:selected",c).length;case"input":if(this.checkable(c))return this.findByName(c.name).filter(":checked").length}return b.length},depend:function(a,b){return!this.dependTypes[typeof a]||this.dependTypes[typeof a](a,b)},dependTypes:{"boolean":function(a){return a},string:function(b,c){return!!a(b,c.form).length},"function":function(a,b){return a(b)}},optional:function(b){var c=this.elementValue(b);return!a.validator.methods.required.call(this,c,b)&&"dependency-mismatch"},startRequest:function(b){this.pending[b.name]||(this.pendingRequest++,a(b).addClass(this.settings.pendingClass),this.pending[b.name]=!0)},stopRequest:function(b,c){this.pendingRequest--,this.pendingRequest<0&&(this.pendingRequest=0),delete this.pending[b.name],a(b).removeClass(this.settings.pendingClass),c&&0===this.pendingRequest&&this.formSubmitted&&this.form()?(a(this.currentForm).submit(),this.submitButton&&a("input:hidden[name='"+this.submitButton.name+"']",this.currentForm).remove(),this.formSubmitted=!1):!c&&0===this.pendingRequest&&this.formSubmitted&&(a(this.currentForm).triggerHandler("invalid-form",[this]),this.formSubmitted=!1)},previousValue:function(b,c){return c="string"==typeof c&&c||"remote",a.data(b,"previousValue")||a.data(b,"previousValue",{old:null,valid:!0,message:this.defaultMessage(b,{method:c})})},destroy:function(){this.resetForm(),a(this.currentForm).off(".validate").removeData("validator").find(".validate-equalTo-blur").off(".validate-equalTo").removeClass("validate-equalTo-blur")}},classRuleSettings:{required:{required:!0},email:{email:!0},url:{url:!0},date:{date:!0},dateISO:{dateISO:!0},number:{number:!0},digits:{digits:!0},creditcard:{creditcard:!0}},addClassRules:function(b,c){b.constructor===String?this.classRuleSettings[b]=c:a.extend(this.classRuleSettings,b)},classRules:function(b){var c={},d=a(b).attr("class");return d&&a.each(d.split(" "),function(){this in a.validator.classRuleSettings&&a.extend(c,a.validator.classRuleSettings[this])}),c},normalizeAttributeRule:function(a,b,c,d){/min|max|step/.test(c)&&(null===b||/number|range|text/.test(b))&&(d=Number(d),isNaN(d)&&(d=void 0)),d||0===d?a[c]=d:b===c&&"range"!==b&&(a[c]=!0)},attributeRules:function(b){var c,d,e={},f=a(b),g=b.getAttribute("type");for(c in a.validator.methods)"required"===c?(d=b.getAttribute(c),""===d&&(d=!0),d=!!d):d=f.attr(c),this.normalizeAttributeRule(e,g,c,d);return e.maxlength&&/-1|2147483647|524288/.test(e.maxlength)&&delete e.maxlength,e},dataRules:function(b){var c,d,e={},f=a(b),g=b.getAttribute("type");for(c in a.validator.methods)d=f.data("rule"+c.charAt(0).toUpperCase()+c.substring(1).toLowerCase()),this.normalizeAttributeRule(e,g,c,d);return e},staticRules:function(b){var c={},d=a.data(b.form,"validator");return d.settings.rules&&(c=a.validator.normalizeRule(d.settings.rules[b.name])||{}),c},normalizeRules:function(b,c){return a.each(b,function(d,e){if(e===!1)return void delete b[d];if(e.param||e.depends){var f=!0;switch(typeof e.depends){case"string":f=!!a(e.depends,c.form).length;break;case"function":f=e.depends.call(c,c)}f?b[d]=void 0===e.param||e.param:(a.data(c.form,"validator").resetElements(a(c)),delete b[d])}}),a.each(b,function(d,e){b[d]=a.isFunction(e)&&"normalizer"!==d?e(c):e}),a.each(["minlength","maxlength"],function(){b[this]&&(b[this]=Number(b[this]))}),a.each(["rangelength","range"],function(){var c;b[this]&&(a.isArray(b[this])?b[this]=[Number(b[this][0]),Number(b[this][1])]:"string"==typeof b[this]&&(c=b[this].replace(/[\[\]]/g,"").split(/[\s,]+/),b[this]=[Number(c[0]),Number(c[1])]))}),a.validator.autoCreateRanges&&(null!=b.min&&null!=b.max&&(b.range=[b.min,b.max],delete b.min,delete b.max),null!=b.minlength&&null!=b.maxlength&&(b.rangelength=[b.minlength,b.maxlength],delete b.minlength,delete b.maxlength)),b},normalizeRule:function(b){if("string"==typeof b){var c={};a.each(b.split(/\s/),function(){c[this]=!0}),b=c}return b},addMethod:function(b,c,d){a.validator.methods[b]=c,a.validator.messages[b]=void 0!==d?d:a.validator.messages[b],c.length<3&&a.validator.addClassRules(b,a.validator.normalizeRule(b))},methods:{required:function(b,c,d){if(!this.depend(d,c))return"dependency-mismatch";if("select"===c.nodeName.toLowerCase()){var e=a(c).val();return e&&e.length>0}return this.checkable(c)?this.getLength(b,c)>0:b.length>0},email:function(a,b){return this.optional(b)||/^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/.test(a)},url:function(a,b){return this.optional(b)||/^(?:(?:(?:https?|ftp):)?\/\/)(?:\S+(?::\S*)?@)?(?:(?!(?:10|127)(?:\.\d{1,3}){3})(?!(?:169\.254|192\.168)(?:\.\d{1,3}){2})(?!172\.(?:1[6-9]|2\d|3[0-1])(?:\.\d{1,3}){2})(?:[1-9]\d?|1\d\d|2[01]\d|22[0-3])(?:\.(?:1?\d{1,2}|2[0-4]\d|25[0-5])){2}(?:\.(?:[1-9]\d?|1\d\d|2[0-4]\d|25[0-4]))|(?:(?:[a-z\u00a1-\uffff0-9]-*)*[a-z\u00a1-\uffff0-9]+)(?:\.(?:[a-z\u00a1-\uffff0-9]-*)*[a-z\u00a1-\uffff0-9]+)*(?:\.(?:[a-z\u00a1-\uffff]{2,})).?)(?::\d{2,5})?(?:[\/?#]\S*)?$/i.test(a)},date:function(a,b){return this.optional(b)||!/Invalid|NaN/.test(new Date(a).toString())},dateISO:function(a,b){return this.optional(b)||/^\d{4}[\/\-](0?[1-9]|1[012])[\/\-](0?[1-9]|[12][0-9]|3[01])$/.test(a)},number:function(a,b){return this.optional(b)||/^(?:-?\d+|-?\d{1,3}(?:,\d{3})+)?(?:\.\d+)?$/.test(a)},digits:function(a,b){return this.optional(b)||/^\d+$/.test(a)},minlength:function(b,c,d){var e=a.isArray(b)?b.length:this.getLength(b,c);return this.optional(c)||e>=d},maxlength:function(b,c,d){var e=a.isArray(b)?b.length:this.getLength(b,c);return this.optional(c)||e<=d},rangelength:function(b,c,d){var e=a.isArray(b)?b.length:this.getLength(b,c);return this.optional(c)||e>=d[0]&&e<=d[1]},min:function(a,b,c){return this.optional(b)||a>=c},max:function(a,b,c){return this.optional(b)||a<=c},range:function(a,b,c){return this.optional(b)||a>=c[0]&&a<=c[1]},step:function(b,c,d){var e,f=a(c).attr("type"),g="Step attribute on input type "+f+" is not supported.",h=["text","number","range"],i=new RegExp("\\b"+f+"\\b"),j=f&&!i.test(h.join()),k=function(a){var b=(""+a).match(/(?:\.(\d+))?$/);return b&&b[1]?b[1].length:0},l=function(a){return Math.round(a*Math.pow(10,e))},m=!0;if(j)throw new Error(g);return e=k(d),(k(b)>e||l(b)%l(d)!==0)&&(m=!1),this.optional(c)||m},equalTo:function(b,c,d){var e=a(d);return this.settings.onfocusout&&e.not(".validate-equalTo-blur").length&&e.addClass("validate-equalTo-blur").on("blur.validate-equalTo",function(){a(c).valid()}),b===e.val()},remote:function(b,c,d,e){if(this.optional(c))return"dependency-mismatch";e="string"==typeof e&&e||"remote";var f,g,h,i=this.previousValue(c,e);return this.settings.messages[c.name]||(this.settings.messages[c.name]={}),i.originalMessage=i.originalMessage||this.settings.messages[c.name][e],this.settings.messages[c.name][e]=i.message,d="string"==typeof d&&{url:d}||d,h=a.param(a.extend({data:b},d.data)),i.old===h?i.valid:(i.old=h,f=this,this.startRequest(c),g={},g[c.name]=b,a.ajax(a.extend(!0,{mode:"abort",port:"validate"+c.name,dataType:"json",data:g,context:f.currentForm,success:function(a){var d,g,h,j=a===!0||"true"===a;f.settings.messages[c.name][e]=i.originalMessage,j?(h=f.formSubmitted,f.resetInternals(),f.toHide=f.errorsFor(c),f.formSubmitted=h,f.successList.push(c),f.invalid[c.name]=!1,f.showErrors()):(d={},g=a||f.defaultMessage(c,{method:e,parameters:b}),d[c.name]=i.message=g,f.invalid[c.name]=!0,f.showErrors(d)),i.valid=j,f.stopRequest(c,j)}},d)),"pending")}}});var b,c={};return a.ajaxPrefilter?a.ajaxPrefilter(function(a,b,d){var e=a.port;"abort"===a.mode&&(c[e]&&c[e].abort(),c[e]=d)}):(b=a.ajax,a.ajax=function(d){var e=("mode"in d?d:a.ajaxSettings).mode,f=("port"in d?d:a.ajaxSettings).port;return"abort"===e?(c[f]&&c[f].abort(),c[f]=b.apply(this,arguments),c[f]):b.apply(this,arguments)}),a});
--------------------------------------------------------------------------------
/reactjs/src/App.jsx:
--------------------------------------------------------------------------------
1 | import React, { Component } from 'react';
2 | import './style/app.scss';
3 | import ChannelList from './components/ChannelList/ChannelList';
4 | // import CreateChannel from './components/CreateChannel/CreateChannel';
5 |
6 | class App extends Component {
7 | componentDidMount() {
8 | // services.setupInterceptors()
9 | }
10 | render() {
11 | return (
12 |
13 | {/* */}
14 |
15 |
16 | );
17 | }
18 | }
19 |
20 |
21 | export default App;
22 |
--------------------------------------------------------------------------------
/reactjs/src/components/ChannelList/ChannelList.css:
--------------------------------------------------------------------------------
1 |
2 | .trash {
3 | padding: 10px;
4 | }
5 | .main-title {
6 | padding-top: 10px;
7 | }
--------------------------------------------------------------------------------
/reactjs/src/components/ChannelList/ChannelList.jsx:
--------------------------------------------------------------------------------
1 | import React, { Component } from 'react';
2 | import { graphql, Mutation, compose } from 'react-apollo';
3 | import gql from 'graphql-tag';
4 | import _ from 'underscore';
5 | import update from 'react-addons-update';
6 | require('./ChannelList.css');
7 |
8 | class ChannelsList extends Component {
9 | constructor(props) {
10 | super(props);
11 | this.state = {
12 | id: "",
13 | nameValue: "",
14 | }
15 | }
16 |
17 | handleKeyUp = (evt) => {
18 | if (evt.keyCode === 13) {
19 | evt.persist();
20 | if (this.state.id !== "") {
21 | this.props.updateChannelMutation({
22 | variables: {
23 | name: evt.target.value,
24 | id: this.state.id
25 | },
26 | }).then((data) => {
27 | evt.target.value = '';
28 | });
29 | this.setState({
30 | id: ""
31 | })
32 | } else {
33 | this.props.createChannelMutation({
34 | variables: {
35 | name: evt.target.value
36 | },
37 | }).then((data) => {
38 | evt.target.value = '';
39 | });
40 | }
41 | };
42 | }
43 |
44 |
45 | componentWillMount() {
46 | this.props.data.subscribeToMore({
47 | document: addChannelSubscription, // Use the subscription
48 | updateQuery: (prev, { subscriptionData }) => {
49 | if (!subscriptionData.data) {
50 | return prev;
51 | }
52 | const newChannel = subscriptionData.data.subscriptionChannelAdded;
53 | // Add check to prevent double adding of channels.
54 | if (!prev.channels.find((channel) => channel.id === newChannel.id)) {
55 | let updatedChannels = Object.assign({}, prev, { channels: [...prev.channels, newChannel] });
56 | return updatedChannels;
57 | } else {
58 | return prev;
59 | }
60 | }
61 | });
62 | this.props.data.subscribeToMore({
63 | document: deleteChannelSubscription, // Use the subscription
64 | updateQuery: (prev, { subscriptionData }) => {
65 | if (!subscriptionData.data) {
66 | return prev;
67 | }
68 | const newChannel = subscriptionData.data.subscriptionChannelDeleted;
69 | const deleteIndex = _.findIndex(prev.channels, (item) => item.id === newChannel.id);
70 | if (deleteIndex < 0) {
71 | return prev;
72 | }
73 | return update(prev, {
74 | channels: {
75 | $splice: [[deleteIndex, 1]]
76 | }
77 | });
78 | }
79 | });
80 | this.props.data.subscribeToMore({
81 | document: updateChannelSubscription, // Use the subscription
82 | updateQuery: (prev, { subscriptionData }) => {
83 | if (!subscriptionData.data) {
84 | return prev;
85 | }
86 | }
87 | });
88 | }
89 |
90 | onEditClick = (ch) => {
91 | this.setState({
92 | nameValue: ch.name,
93 | id: ch.id
94 | });
95 | }
96 | onChangeFunc = (event) => {
97 | this.setState({
98 | nameValue: event.target.value
99 | })
100 | }
101 | render() {
102 | const { data: { loading, error, channels } } = this.props;
103 | if (loading) {
104 | return Loading ...
;
105 | }
106 | if (error) {
107 | return {error.message}
;
108 | }
109 | return (
110 |
111 |
112 |
113 |
Channel List
114 |
115 |
116 |
123 |
124 |
125 | {channels.map(ch =>
126 | -
127 |
130 |
140 |
141 | )}
142 |
143 |
144 |
145 |
146 | )
147 |
148 | }
149 |
150 | }
151 |
152 | export const channelsListQuery = gql`
153 | query ChannelsListQuery {
154 | channels {
155 | id
156 | name
157 | }
158 | }
159 | `;
160 |
161 | const addChannelSubscription = gql`
162 | subscription Channels {
163 | subscriptionChannelAdded {
164 | id
165 | name
166 | }
167 | }
168 | `
169 |
170 | const deleteChannelSubscription = gql`
171 | subscription Channels {
172 | subscriptionChannelDeleted {
173 | id
174 | name
175 | }
176 | }
177 | `
178 | const updateChannelSubscription = gql`
179 | subscription Channels {
180 | subscriptionChannelUpdated {
181 | id
182 | name
183 | }
184 | }
185 | `
186 | const deleteChannel = gql`
187 | mutation deleteChannelMutation($id: Int!) {
188 | deleteChannel(ID: $id) {
189 | id
190 | name
191 | }
192 | }
193 | `;
194 |
195 | const updateChannel = gql`
196 | mutation updateChannelMutation($id: Int!,$name:String!) {
197 | updateChannel(id: $id,name:$name) {
198 | id
199 | name
200 | }
201 | }
202 | `;
203 |
204 | const CreateChannelMutation = gql`
205 | mutation addChannel($name: String!) {
206 | addChannel(name: $name) {
207 | id
208 | name
209 | }
210 | }
211 | `;
212 | const multipleMutation = compose(
213 | graphql(CreateChannelMutation, { name: 'createChannelMutation' }),
214 | graphql(updateChannel, { name: 'updateChannelMutation' })
215 | )
216 |
217 | export default compose(multipleMutation, graphql(channelsListQuery))(ChannelsList);
218 |
--------------------------------------------------------------------------------
/reactjs/src/environment.jsx:
--------------------------------------------------------------------------------
1 |
2 | // export const Host = "192.168.0.2"
3 | export const Host = "localhost"
4 | export const Port = "8888";
5 |
6 | export const BASE_API = "http://"+Host+":"+Port+"/";
7 | export const WSHost = "ws://"+Host+":"+Port+"/query";
8 |
--------------------------------------------------------------------------------
/reactjs/src/index.js:
--------------------------------------------------------------------------------
1 | import React from 'react';
2 | import ReactDOM from 'react-dom';
3 | import { ApolloProvider } from 'react-apollo';
4 | import ApolloClient from 'apollo-client';
5 | import App from './App';
6 | import {WebSocketLink} from 'apollo-link-ws';
7 | // import { SubscriptionClient } from 'subscriptions-transport-ws';
8 | import { InMemoryCache } from 'apollo-cache-inmemory';
9 | import * as environment from "./environment";
10 |
11 | const wsLink = new WebSocketLink({
12 | uri: environment.WSHost,
13 | options: {
14 | reconnect: true,
15 | connectionParams: {
16 | Authorization: `Bearer ${localStorage.getItem('auth_token')}`
17 | },
18 | }
19 | });
20 | const apolloClient = new ApolloClient({
21 | link: wsLink,
22 | cache: new InMemoryCache(),
23 | });
24 |
25 | if (module.hot) {
26 | module.hot.accept('./App', () => {
27 | const NextApp = require('./App').default;
28 | render();
29 | })
30 | }
31 |
32 | function render(component) {
33 | ReactDOM.render(
34 | {component}
35 | , document.getElementById('root'));
36 | }
37 |
38 | render();
39 |
--------------------------------------------------------------------------------
/reactjs/src/style/app.scss:
--------------------------------------------------------------------------------
1 | .center {
2 | text-align: center;
3 | }
--------------------------------------------------------------------------------