Refactor reports query, tests

- Query returns an array of Reports with all the filedReports that
belong to them
- Mutation returns the same
This commit is contained in:
mattwr18 2019-11-26 21:34:21 +01:00
parent 2f249a73c5
commit eceeecd9b7
4 changed files with 165 additions and 102 deletions

View File

@ -19,7 +19,7 @@ export default {
WITH submitter, resource, report
CREATE (report)<-[filed:FILED {createdAt: $createdAt, reasonCategory: $reasonCategory, reasonDescription: $reasonDescription}]-(submitter)
RETURN submitter, report, filed, resource, labels(resource)[0] AS type
RETURN submitter, report, resource, labels(resource)[0] AS type
`,
{
resourceId,
@ -32,7 +32,6 @@ export default {
return reportRelationshipTransactionResponse.records.map(record => ({
submitter: record.get('submitter').properties,
report: record.get('report').properties,
filed: record.get('filed').properties,
resource: record.get('resource').properties,
type: record.get('type'),
}))
@ -40,10 +39,9 @@ export default {
try {
const txResult = await writeTxResultPromise
if (!txResult[0]) return null
const { submitter, report, filed, resource, type } = txResult[0]
const { submitter, report, resource, type } = txResult[0]
createdRelationshipWithNestedAttributes = {
...filed,
report,
...report,
post: null,
comment: null,
user: null,
@ -74,10 +72,10 @@ export default {
let reports, orderByClause
switch (params.orderBy) {
case 'createdAt_asc':
orderByClause = 'ORDER BY report.createdAt ASC, filed.createdAt DESC'
orderByClause = 'ORDER BY report.createdAt ASC'
break
case 'createdAt_desc':
orderByClause = 'ORDER BY report.createdAt DESC, filed.createdAt DESC'
orderByClause = 'ORDER BY report.createdAt DESC'
break
default:
orderByClause = ''
@ -87,7 +85,7 @@ export default {
`
MATCH (submitter:User)-[filed:FILED]->(report:Report)-[:BELONGS_TO]->(resource)
WHERE resource:User OR resource:Post OR resource:Comment
RETURN submitter, report, filed, resource, labels(resource)[0] as type
RETURN submitter, report, resource, labels(resource)[0] as type
${orderByClause}
`,
{},
@ -95,7 +93,6 @@ export default {
return allReportsTransactionResponse.records.map(record => ({
submitter: record.get('submitter').properties,
report: record.get('report').properties,
filed: record.get('filed').properties,
resource: record.get('resource').properties,
type: record.get('type'),
}))
@ -104,10 +101,9 @@ export default {
const txResult = await readTxPromise
if (!txResult[0]) return null
reports = txResult.map(reportedRecord => {
const { report, submitter, filed, resource, type } = reportedRecord
const { report, submitter, resource, type } = reportedRecord
const relationshipWithNestedAttributes = {
...report,
filed,
post: null,
comment: null,
user: null,
@ -133,4 +129,40 @@ export default {
return reports
},
},
Report: {
reportsFiled: async (parent, _params, context, _resolveInfo) => {
if (typeof parent.reportsFiled !== 'undefined') return parent.reportsFiled
const session = context.driver.session()
const { id } = parent
let reportsFiled
const readTxPromise = session.readTransaction(async tx => {
const allReportsTransactionResponse = await tx.run(
`
MATCH (submitter:User)-[filed:FILED]->(report:Report {id: $id})
RETURN filed, submitter
`,
{ id },
)
return allReportsTransactionResponse.records.map(record => ({
submitter: record.get('submitter').properties,
filed: record.get('filed').properties,
}))
})
try {
const txResult = await readTxPromise
if (!txResult[0]) return null
reportsFiled = txResult.map(reportedRecord => {
const { submitter, filed } = reportedRecord
const relationshipWithNestedAttributes = {
...filed,
submitter,
}
return relationshipWithNestedAttributes
})
} finally {
session.close()
}
return reportsFiled
},
},
}

View File

@ -18,13 +18,12 @@ describe('file a report on a resource', () => {
reasonCategory: $reasonCategory
reasonDescription: $reasonDescription
) {
id
createdAt
reasonCategory
reasonDescription
updatedAt
disable
closed
type
submitter {
email
}
user {
name
}
@ -34,12 +33,13 @@ describe('file a report on a resource', () => {
comment {
content
}
report {
reportsFiled {
submitter {
id
}
createdAt
updatedAt
disable
closed
reasonCategory
reasonDescription
}
}
}
@ -129,14 +129,15 @@ describe('file a report on a resource', () => {
).resolves.toMatchObject({
data: {
fileReport: {
type: 'User',
report: {
id: expect.any(String),
createdAt: expect.any(String),
updatedAt: expect.any(String),
disable: false,
closed: false,
user: {
name: 'abusive-user',
},
type: 'User',
},
},
errors: undefined,
@ -153,7 +154,7 @@ describe('file a report on a resource', () => {
mutation: reportMutation,
variables: { ...variables, resourceId: 'abusive-user-id' },
})
expect(firstReport.data.fileReport.report).toEqual(secondReport.data.fileReport.report)
expect(firstReport.data.fileReport.id).toEqual(secondReport.data.fileReport.id)
})
it.todo('creates multiple reports')
@ -169,7 +170,22 @@ describe('file a report on a resource', () => {
).resolves.toMatchObject({
data: {
fileReport: {
id: expect.any(String),
createdAt: expect.any(String),
updatedAt: expect.any(String),
disable: false,
closed: false,
type: 'User',
reportsFiled: [
{
submitter: {
id: 'current-user-id',
},
createdAt: expect.any(String),
reasonCategory: 'other',
reasonDescription: 'Violates code of conduct !!!',
},
],
},
},
errors: undefined,
@ -203,10 +219,14 @@ describe('file a report on a resource', () => {
).resolves.toMatchObject({
data: {
fileReport: {
reportsFiled: [
{
submitter: {
email: 'test@example.org',
id: 'current-user-id',
},
},
],
},
},
errors: undefined,
})
@ -241,8 +261,12 @@ describe('file a report on a resource', () => {
).resolves.toMatchObject({
data: {
fileReport: {
reportsFiled: [
{
reasonCategory: 'criminal_behavior_violation_german_law',
},
],
},
},
errors: undefined,
})
@ -282,8 +306,12 @@ describe('file a report on a resource', () => {
).resolves.toMatchObject({
data: {
fileReport: {
reportsFiled: [
{
reasonDescription: 'My reason!',
},
],
},
},
errors: undefined,
})
@ -302,8 +330,12 @@ describe('file a report on a resource', () => {
).resolves.toMatchObject({
data: {
fileReport: {
reportsFiled: [
{
reasonDescription: 'My reason !',
},
],
},
},
errors: undefined,
})
@ -469,12 +501,11 @@ describe('file a report on a resource', () => {
const reportsQuery = gql`
query {
reports(orderBy: createdAt_desc) {
createdAt
reasonCategory
reasonDescription
submitter {
id
}
createdAt
updatedAt
disable
closed
type
user {
id
@ -485,12 +516,13 @@ describe('file a report on a resource', () => {
comment {
id
}
report {
reportsFiled {
submitter {
id
}
createdAt
updatedAt
disable
closed
reasonCategory
reasonDescription
}
}
}
@ -602,67 +634,73 @@ describe('file a report on a resource', () => {
const expected = {
reports: expect.arrayContaining([
expect.objectContaining({
id: expect.any(String),
createdAt: expect.any(String),
reasonCategory: 'doxing',
reasonDescription: 'This user is harassing me with bigoted remarks',
submitter: expect.objectContaining({
id: 'current-user-id',
}),
updatedAt: expect.any(String),
disable: false,
closed: false,
type: 'User',
user: expect.objectContaining({
id: 'abusive-user-1',
}),
post: null,
comment: null,
report: {
reportsFiled: expect.arrayContaining([
expect.objectContaining({
submitter: expect.objectContaining({
id: 'current-user-id',
}),
createdAt: expect.any(String),
reasonCategory: 'doxing',
reasonDescription: 'This user is harassing me with bigoted remarks',
}),
]),
}),
expect.objectContaining({
id: expect.any(String),
createdAt: expect.any(String),
updatedAt: expect.any(String),
disable: false,
closed: false,
},
}),
expect.objectContaining({
createdAt: expect.any(String),
reasonCategory: 'other',
reasonDescription: 'This comment is bigoted',
submitter: expect.objectContaining({
id: 'current-user-id',
}),
type: 'Post',
user: null,
post: expect.objectContaining({
id: 'abusive-post-1',
}),
comment: null,
report: {
reportsFiled: expect.arrayContaining([
expect.objectContaining({
submitter: expect.objectContaining({
id: 'current-user-id',
}),
createdAt: expect.any(String),
reasonCategory: 'other',
reasonDescription: 'This comment is bigoted',
}),
]),
}),
expect.objectContaining({
id: expect.any(String),
createdAt: expect.any(String),
updatedAt: expect.any(String),
disable: false,
closed: false,
},
}),
expect.objectContaining({
createdAt: expect.any(String),
reasonCategory: 'discrimination_etc',
reasonDescription: 'This post is bigoted',
submitter: expect.objectContaining({
id: 'current-user-id',
}),
type: 'Comment',
user: null,
post: null,
comment: expect.objectContaining({
id: 'abusive-comment-1',
}),
report: {
id: expect.any(String),
reportsFiled: expect.arrayContaining([
expect.objectContaining({
submitter: expect.objectContaining({
id: 'current-user-id',
}),
createdAt: expect.any(String),
updatedAt: expect.any(String),
disable: false,
closed: false,
},
reasonCategory: 'discrimination_etc',
reasonDescription: 'This post is bigoted',
}),
]),
}),
]),
}

View File

@ -2,17 +2,7 @@ type FILED {
createdAt: String!
reasonCategory: ReasonCategory!
reasonDescription: String!
report: Report @cypher(
statement: "MATCH (resource)<-[:BELONGS_TO]-(report:Report)<-[:FILED]-(:User) WHERE NOT resource.deleted = true AND NOT resource.disabled = true RETURN report"
)
submitter: User
# @cypher(statement: "MATCH (resource)<-[:FILED]-(user:User) RETURN user")
type: String
# @cypher(statement: "MATCH (resource)<-[:FILED]-(user:User) RETURN labels(resource)[0]")
user: User
post: Post
comment: Comment
}
# this list equals the strings of an array in file "webapp/constants/modals.js"
@ -34,11 +24,3 @@ enum ReportOrdering {
createdAt_asc
createdAt_desc
}
type Query {
reports(orderBy: ReportOrdering): [FILED]
}
type Mutation {
fileReport(resourceId: ID!, reasonCategory: ReasonCategory!, reasonDescription: String!): FILED
}

View File

@ -5,12 +5,23 @@ type Report {
rule: ReportRule!
disable: Boolean!
closed: Boolean!
resource: ReportResource
filed: [FILED]
reportsFiled: [FILED]
user: User
post: Post
comment: Comment
type: String
}
# not yet supported
union ReportResource = User | Post | Comment
# union ReportResource = User | Post | Comment
enum ReportRule {
latestReviewUpdatedAtRules
}
type Mutation {
fileReport(resourceId: ID!, reasonCategory: ReasonCategory!, reasonDescription: String!): Report
}
type Query {
reports(orderBy: ReportOrdering): [Report]
}