mirror of
https://github.com/kremalicious/blog.git
synced 2024-12-22 17:23:50 +01:00
typescript fixes
This commit is contained in:
parent
0a8b5eda9d
commit
51a819de44
@ -19,6 +19,7 @@
|
||||
"plugin:prettier/recommended",
|
||||
"plugin:react/recommended"
|
||||
],
|
||||
"plugins": ["@typescript-eslint", "react"],
|
||||
"rules": {
|
||||
"object-curly-spacing": ["error", "always"],
|
||||
"react/prop-types": "off",
|
||||
|
@ -1,13 +1,17 @@
|
||||
module.exports = {
|
||||
transform: {
|
||||
'^.+\\.tsx?$': '<rootDir>/jest/jest-preprocess.js'
|
||||
'^.+\\.(tsx?|jsx?)$': 'ts-jest',
|
||||
'^.+\\.jsx?$': '<rootDir>/jest/jest-preprocess.js'
|
||||
},
|
||||
testRegex: '(/__tests__/.*|\\.(test|spec))\\.(ts|tsx)$',
|
||||
|
||||
moduleNameMapper: {
|
||||
'.+\\.(css|styl|less|sass|scss)$': 'identity-obj-proxy',
|
||||
'.+\\.(jpg|jpeg|png|gif|eot|otf|webp|ttf|woff|woff2|mp4|webm|wav|mp3|m4a|aac|oga)$':
|
||||
'<rootDir>/jest/__mocks__/file-mock.js',
|
||||
'\\.svg': '<rootDir>/jest/__mocks__/svgr-mock.js'
|
||||
'<rootDir>/jest/__mocks__/file-mock.ts',
|
||||
'\\.svg': '<rootDir>/jest/__mocks__/svgr-mock.ts'
|
||||
},
|
||||
moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx', 'json', 'node'],
|
||||
testPathIgnorePatterns: ['node_modules', '.cache', 'public', 'coverage'],
|
||||
transformIgnorePatterns: ['node_modules/(?!(gatsby)/)'],
|
||||
globals: {
|
||||
@ -15,6 +19,6 @@ module.exports = {
|
||||
},
|
||||
testURL: 'http://localhost',
|
||||
setupFiles: ['<rootDir>/jest/loadershim.js'],
|
||||
setupFilesAfterEnv: ['<rootDir>/jest/setup-test-env.js'],
|
||||
setupFilesAfterEnv: ['<rootDir>/jest/setup-test-env.ts'],
|
||||
collectCoverageFrom: ['src/**/*.{ts,tsx}', '!src/@types/**/*']
|
||||
}
|
||||
|
@ -1 +0,0 @@
|
||||
module.exports = 'test-file-stub'
|
1
jest/__mocks__/file-mock.ts
Normal file
1
jest/__mocks__/file-mock.ts
Normal file
@ -0,0 +1 @@
|
||||
export default 'test-file-stub'
|
@ -1,13 +1,13 @@
|
||||
const React = require('react')
|
||||
import React from 'react'
|
||||
const gatsby = jest.requireActual('gatsby')
|
||||
|
||||
module.exports = {
|
||||
export default {
|
||||
...gatsby,
|
||||
graphql: jest.fn(),
|
||||
Link: jest.fn().mockImplementation(
|
||||
// these props are invalid for an `a` tag
|
||||
({
|
||||
/* eslint-disable no-unused-vars */
|
||||
/* eslint-disable @typescript-eslint/no-unused-vars */
|
||||
activeClassName,
|
||||
activeStyle,
|
||||
getProps,
|
||||
@ -15,7 +15,7 @@ module.exports = {
|
||||
ref,
|
||||
replace,
|
||||
to,
|
||||
/* eslint-enable no-unused-vars */
|
||||
/* eslint-enable @typescript-eslint/no-unused-vars */
|
||||
...rest
|
||||
}) =>
|
||||
React.createElement('a', {
|
@ -1 +0,0 @@
|
||||
module.exports = { ReactComponent: 'svg' }
|
3
jest/__mocks__/svgr-mock.ts
Normal file
3
jest/__mocks__/svgr-mock.ts
Normal file
@ -0,0 +1,3 @@
|
||||
const content = 'svg'
|
||||
export const ReactComponent = content
|
||||
export default content
|
@ -1 +0,0 @@
|
||||
require('@testing-library/jest-dom/extend-expect')
|
1
jest/setup-test-env.ts
Normal file
1
jest/setup-test-env.ts
Normal file
@ -0,0 +1 @@
|
||||
import '@testing-library/jest-dom/extend-expect'
|
@ -18,6 +18,7 @@
|
||||
"lint:css": "stylelint 'src/**/*.{css,scss}'",
|
||||
"lint:md": "markdownlint './**/*.{md,markdown}' --ignore './{node_modules,public,.cache,.git,coverage}/**/*'",
|
||||
"format": "prettier --write 'src/**/*.{js,jsx,ts,tsx,md,json,css,scss}'",
|
||||
"tsc": "tsc --noEmit",
|
||||
"deploy": "./scripts/deploy.sh",
|
||||
"new": "babel-node ./scripts/new.js"
|
||||
},
|
||||
@ -90,6 +91,7 @@
|
||||
"@testing-library/react": "^9.2.0",
|
||||
"@types/classnames": "^2.2.9",
|
||||
"@types/jest": "^24.0.18",
|
||||
"@types/lunr": "^2.3.2",
|
||||
"@types/node": "^12.7.8",
|
||||
"@types/react": "^16.9.4",
|
||||
"@types/react-dom": "^16.9.1",
|
||||
@ -124,6 +126,7 @@
|
||||
"stylelint-config-prettier": "^6.0.0",
|
||||
"stylelint-config-standard": "^19.0.0",
|
||||
"stylelint-prettier": "^1.1.1",
|
||||
"ts-jest": "^24.1.0",
|
||||
"typescript": "^3.6.3",
|
||||
"why-did-you-update": "^1.0.6"
|
||||
},
|
||||
|
29
src/@types/global.d.ts
vendored
29
src/@types/global.d.ts
vendored
@ -1,23 +1,18 @@
|
||||
interface CSSModule {
|
||||
[className: string]: string
|
||||
}
|
||||
|
||||
// type shims for CSS modules
|
||||
declare module '*.module.scss' {
|
||||
const cssModule: CSSModule
|
||||
export = cssModule
|
||||
}
|
||||
|
||||
declare module '*.module.css' {
|
||||
const cssModule: CSSModule
|
||||
export = cssModule
|
||||
const classes: { [key: string]: string }
|
||||
export default classes
|
||||
}
|
||||
|
||||
/* eslint-disable-next-line @typescript-eslint/no-empty-interface */
|
||||
interface SvgrComponent
|
||||
extends React.StatelessComponent<React.SVGAttributes<SVGElement>> {}
|
||||
declare module '*.module.scss' {
|
||||
const classes: { [key: string]: string }
|
||||
export default classes
|
||||
}
|
||||
|
||||
declare module '*.svg' {
|
||||
const value: SvgrComponent
|
||||
export default value
|
||||
import * as React from 'react'
|
||||
export const ReactComponent: React.FunctionComponent<
|
||||
React.SVGProps<SVGSVGElement>
|
||||
>
|
||||
const src: string
|
||||
export default src
|
||||
}
|
||||
|
5
src/@types/node_modules.d.ts
vendored
Normal file
5
src/@types/node_modules.d.ts
vendored
Normal file
@ -0,0 +1,5 @@
|
||||
declare module 'pigeon-maps'
|
||||
declare module 'pigeon-marker'
|
||||
declare module 'react-blockies'
|
||||
declare module 'react-time'
|
||||
declare module 'remark-react'
|
1
src/@types/pigeon-maps.d.ts
vendored
1
src/@types/pigeon-maps.d.ts
vendored
@ -1 +0,0 @@
|
||||
declare module 'pigeon-maps'
|
1
src/@types/pigeon-marker.d.ts
vendored
1
src/@types/pigeon-marker.d.ts
vendored
@ -1 +0,0 @@
|
||||
declare module 'pigeon-marker'
|
1
src/@types/react-blockies.d.ts
vendored
1
src/@types/react-blockies.d.ts
vendored
@ -1 +0,0 @@
|
||||
declare module 'react-blockies'
|
1
src/@types/react-time.d.ts
vendored
1
src/@types/react-time.d.ts
vendored
@ -1 +0,0 @@
|
||||
declare module 'react-time'
|
1
src/@types/remark-react.d.ts
vendored
1
src/@types/remark-react.d.ts
vendored
@ -1 +0,0 @@
|
||||
declare module 'remark-react'
|
@ -5,6 +5,7 @@ import Container from '../atoms/Container'
|
||||
import PostTeaser from '../Post/PostTeaser'
|
||||
import SearchResultsEmpty from './SearchResultsEmpty'
|
||||
import styles from './SearchResults.module.scss'
|
||||
import { GatsbyImageProps } from 'gatsby-image'
|
||||
|
||||
const query = graphql`
|
||||
query {
|
||||
@ -29,6 +30,22 @@ const query = graphql`
|
||||
}
|
||||
`
|
||||
|
||||
interface Page {
|
||||
slug: string
|
||||
}
|
||||
|
||||
interface PostNode {
|
||||
node: {
|
||||
id: string
|
||||
fields: { slug: string }
|
||||
frontmatter: {
|
||||
title: string
|
||||
type: string
|
||||
image: { childImageSharp: GatsbyImageProps }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export default function SearchResults({
|
||||
searchQuery,
|
||||
results,
|
||||
@ -48,13 +65,13 @@ export default function SearchResults({
|
||||
<Container>
|
||||
{results.length > 0 ? (
|
||||
<ul>
|
||||
{results.map(page =>
|
||||
{results.map((page: Page) =>
|
||||
posts
|
||||
.filter(post => post.node.fields.slug === page.slug)
|
||||
.map(({ node }: { node: any }) => (
|
||||
.filter((post: PostNode) => post.node.fields.slug === page.slug)
|
||||
.map((post: PostNode) => (
|
||||
<PostTeaser
|
||||
key={page.slug}
|
||||
post={node}
|
||||
post={post.node}
|
||||
toggleSearch={toggleSearch}
|
||||
/>
|
||||
))
|
||||
|
@ -1,45 +0,0 @@
|
||||
import React from 'react'
|
||||
import { render, fireEvent } from '@testing-library/react'
|
||||
|
||||
import Search from '.'
|
||||
import { useStaticQuery } from 'gatsby'
|
||||
|
||||
describe('Search', () => {
|
||||
beforeEach(() => {
|
||||
useStaticQuery.mockImplementation(() => {
|
||||
return {
|
||||
allMarkdownRemark: {
|
||||
edges: [
|
||||
{
|
||||
node: {
|
||||
id: 'ddd',
|
||||
frontmatter: {
|
||||
title: 'Hello',
|
||||
image: {
|
||||
childImageSharp: 'hello'
|
||||
}
|
||||
},
|
||||
fields: {
|
||||
slug: '/hello/'
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
const portalRoot = document.createElement('div')
|
||||
portalRoot.setAttribute('id', 'document')
|
||||
document.body.appendChild(portalRoot)
|
||||
})
|
||||
|
||||
it('can be opened', () => {
|
||||
const { getByTitle, getByPlaceholderText } = render(<Search lng="en" />)
|
||||
fireEvent.click(getByTitle('Search'))
|
||||
fireEvent.change(getByPlaceholderText('Search everything'), {
|
||||
target: { value: 'hello' }
|
||||
})
|
||||
fireEvent.click(getByTitle('Close search'))
|
||||
})
|
||||
})
|
@ -1,12 +1,26 @@
|
||||
import React, { useState } from 'react'
|
||||
import Helmet from 'react-helmet'
|
||||
import { Helmet } from 'react-helmet'
|
||||
import { CSSTransition } from 'react-transition-group'
|
||||
import lunr from 'lunr'
|
||||
import SearchInput from './SearchInput'
|
||||
import SearchButton from './SearchButton'
|
||||
import SearchResults from './SearchResults'
|
||||
|
||||
import styles from './index.module.scss'
|
||||
|
||||
declare global {
|
||||
interface Window {
|
||||
__LUNR__: {
|
||||
readonly [language: string]: {
|
||||
readonly index: lunr.Index
|
||||
readonly store: {
|
||||
readonly [key: string]: any
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function getSearchResults(query: string, lng: string) {
|
||||
if (!query || !window.__LUNR__) return []
|
||||
const lunrIndex = window.__LUNR__[lng]
|
||||
|
@ -21,7 +21,7 @@ export default function Alerts({
|
||||
message
|
||||
}: {
|
||||
transactionHash: string | null
|
||||
message: { text: MessageChannel; status: string } | null
|
||||
message: { text?: MessageChannel; status?: string } | null
|
||||
}) {
|
||||
const constructMessage = () => {
|
||||
let messageOutput
|
||||
@ -53,7 +53,7 @@ export default function Alerts({
|
||||
return (
|
||||
<div
|
||||
className={classes()}
|
||||
dangerouslySetInnerHTML={{ __html: constructMessage() }}
|
||||
dangerouslySetInnerHTML={{ __html: `${constructMessage()}` }}
|
||||
/>
|
||||
)
|
||||
}
|
||||
|
@ -3,7 +3,7 @@ import { getFiat } from './utils'
|
||||
import styles from './Conversion.module.scss'
|
||||
|
||||
export default class Conversion extends PureComponent<
|
||||
{ amount: string },
|
||||
{ amount: number },
|
||||
{ euro: string; dollar: string }
|
||||
> {
|
||||
state = {
|
||||
|
@ -10,7 +10,7 @@ export default function InputGroup({
|
||||
sendTransaction,
|
||||
selectedAccount
|
||||
}: {
|
||||
amount: string
|
||||
amount: number
|
||||
onAmountChange(target: any): void
|
||||
sendTransaction(): void
|
||||
selectedAccount?: string | null
|
||||
|
@ -1,5 +1,5 @@
|
||||
import React, { PureComponent } from 'react'
|
||||
import PropTypes from 'prop-types'
|
||||
import Web3 from 'web3'
|
||||
import InputGroup from './InputGroup'
|
||||
import Alerts, { alertMessages } from './Alerts'
|
||||
import styles from './index.module.scss'
|
||||
@ -9,26 +9,40 @@ const ONE_SECOND = 1000
|
||||
const ONE_MINUTE = ONE_SECOND * 60
|
||||
const correctNetwork = 1
|
||||
|
||||
export default class Web3Donation extends PureComponent {
|
||||
interface Web3DonationState {
|
||||
netId: number
|
||||
networkName: string
|
||||
accounts: string[]
|
||||
selectedAccount: string
|
||||
amount: number
|
||||
transactionHash: string
|
||||
receipt: string
|
||||
message: {
|
||||
status?: string
|
||||
text?: string
|
||||
}
|
||||
inTransaction: boolean
|
||||
}
|
||||
|
||||
export default class Web3Donation extends PureComponent<
|
||||
{ address: string },
|
||||
Web3DonationState
|
||||
> {
|
||||
state = {
|
||||
netId: null,
|
||||
networkName: null,
|
||||
accounts: [],
|
||||
selectedAccount: null,
|
||||
amount: '0.01',
|
||||
transactionHash: null,
|
||||
receipt: null,
|
||||
message: null,
|
||||
netId: 0,
|
||||
networkName: '',
|
||||
accounts: [''],
|
||||
selectedAccount: '',
|
||||
amount: 0.01,
|
||||
transactionHash: '',
|
||||
receipt: '',
|
||||
message: {},
|
||||
inTransaction: false
|
||||
}
|
||||
|
||||
static propTypes = {
|
||||
address: PropTypes.string
|
||||
}
|
||||
|
||||
web3 = null
|
||||
interval = null
|
||||
networkInterval = null
|
||||
web3: Web3 = null
|
||||
interval: any = null
|
||||
networkInterval: any = null
|
||||
|
||||
componentDidMount() {
|
||||
this.initWeb3()
|
||||
@ -47,10 +61,15 @@ export default class Web3Donation extends PureComponent {
|
||||
this.web3
|
||||
? this.initAllTheTings()
|
||||
: this.setState({
|
||||
message: { status: 'error', text: alertMessages().noWeb3 }
|
||||
message: {
|
||||
status: 'error',
|
||||
text: alertMessages().noWeb3
|
||||
}
|
||||
})
|
||||
} catch (error) {
|
||||
this.setState({ message: { status: 'error', text: error } })
|
||||
this.setState({
|
||||
message: { status: 'error', text: error }
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@ -106,7 +125,10 @@ export default class Web3Donation extends PureComponent {
|
||||
})
|
||||
} else {
|
||||
this.setState({
|
||||
message: { status: 'error', text: alertMessages().noAccount }
|
||||
message: {
|
||||
status: 'error',
|
||||
text: alertMessages().noAccount
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -132,16 +154,21 @@ export default class Web3Donation extends PureComponent {
|
||||
})
|
||||
})
|
||||
.on('error', error =>
|
||||
this.setState({ message: { status: 'error', text: error } })
|
||||
this.setState({
|
||||
message: { status: 'error', text: error.message }
|
||||
})
|
||||
)
|
||||
.then(() => {
|
||||
this.setState({
|
||||
message: { status: 'success', text: alertMessages().success }
|
||||
message: {
|
||||
status: 'success',
|
||||
text: alertMessages().success
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
onAmountChange = ({ target }) => {
|
||||
onAmountChange = ({ target }: { target: any }) => {
|
||||
this.setState({ amount: target.value })
|
||||
}
|
||||
|
||||
|
@ -1,8 +1,18 @@
|
||||
import Web3 from 'web3'
|
||||
|
||||
declare global {
|
||||
interface Window {
|
||||
ethereum: any
|
||||
web3: Web3
|
||||
}
|
||||
|
||||
interface Console {
|
||||
[key: string]: any
|
||||
}
|
||||
}
|
||||
|
||||
export class Logger {
|
||||
static dispatch(verb: any, ...args: any) {
|
||||
// eslint-disable-next-line no-console
|
||||
console[verb](...args)
|
||||
}
|
||||
|
||||
|
@ -10,6 +10,7 @@ const exif = {
|
||||
fstop: '7.2',
|
||||
shutterspeed: '200',
|
||||
focalLength: '200',
|
||||
lensModel: 'Hello',
|
||||
exposure: '200',
|
||||
gps: { latitude: '52.4792516', longitude: '13.431609' }
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
import React from 'react'
|
||||
import { graphql, useStaticQuery } from 'gatsby'
|
||||
import Helmet from 'react-helmet'
|
||||
import { Helmet } from 'react-helmet'
|
||||
import { useSiteMetadata } from '../../hooks/use-site-metadata'
|
||||
|
||||
const query = graphql`
|
||||
@ -15,69 +15,55 @@ const query = graphql`
|
||||
}
|
||||
`
|
||||
|
||||
const createSchemaOrg = (
|
||||
blogURL: string,
|
||||
title: string,
|
||||
postSEO: boolean,
|
||||
postURL: string,
|
||||
image: string,
|
||||
description: string
|
||||
) => {
|
||||
const schemaOrgJSONLD = [
|
||||
{
|
||||
'@context': 'http://schema.org',
|
||||
'@type': 'WebSite',
|
||||
url: blogURL,
|
||||
name: title
|
||||
}
|
||||
]
|
||||
// const createSchemaOrg = (
|
||||
// blogURL: string,
|
||||
// title: string,
|
||||
// postSEO: boolean,
|
||||
// postURL: string,
|
||||
// image: string,
|
||||
// description: string,
|
||||
// author?: string
|
||||
// ) => {
|
||||
// const schemaOrgJSONLD: any = [
|
||||
// {
|
||||
// '@context': 'http://schema.org',
|
||||
// '@type': 'WebSite',
|
||||
// url: blogURL,
|
||||
// name: title
|
||||
// }
|
||||
// ]
|
||||
|
||||
if (postSEO) {
|
||||
schemaOrgJSONLD.push(
|
||||
{
|
||||
'@context': 'http://schema.org',
|
||||
'@type': 'BreadcrumbList',
|
||||
itemListElement: [
|
||||
{
|
||||
'@type': 'ListItem',
|
||||
position: 1,
|
||||
item: {
|
||||
'@id': postURL,
|
||||
name: title,
|
||||
image
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
'@context': 'http://schema.org',
|
||||
'@type': 'BlogPosting',
|
||||
url: blogURL,
|
||||
name: title,
|
||||
headline: title,
|
||||
image: {
|
||||
'@type': 'ImageObject',
|
||||
url: image
|
||||
},
|
||||
description
|
||||
}
|
||||
)
|
||||
}
|
||||
return schemaOrgJSONLD
|
||||
}
|
||||
// if (postSEO) {
|
||||
// schemaOrgJSONLD.push({
|
||||
// '@context': 'http://schema.org',
|
||||
// '@type': 'BlogPosting',
|
||||
// author,
|
||||
// publisher: author,
|
||||
// url: postURL,
|
||||
// name: title,
|
||||
// headline: title,
|
||||
// image: {
|
||||
// '@type': 'ImageObject',
|
||||
// url: image
|
||||
// },
|
||||
// description
|
||||
// })
|
||||
// }
|
||||
// return schemaOrgJSONLD
|
||||
// }
|
||||
|
||||
const MetaTags = ({
|
||||
description,
|
||||
image,
|
||||
url,
|
||||
schema,
|
||||
// schema,
|
||||
postSEO,
|
||||
title
|
||||
}: {
|
||||
description: string
|
||||
image: string
|
||||
url: string
|
||||
schema: string
|
||||
// schema: string
|
||||
postSEO: boolean
|
||||
title: string
|
||||
}) => {
|
||||
@ -96,7 +82,7 @@ const MetaTags = ({
|
||||
<link rel="canonical" href={url} />
|
||||
|
||||
{/* Schema.org tags */}
|
||||
<script type="application/ld+json">{schema}</script>
|
||||
{/* <script type="application/ld+json">{schema}</script> */}
|
||||
|
||||
{/* OpenGraph tags */}
|
||||
<meta property="og:url" content={url} />
|
||||
@ -161,23 +147,22 @@ export default function SEO({
|
||||
const blogURL = siteUrl
|
||||
const url = postSEO ? postURL : blogURL
|
||||
|
||||
let schema = createSchemaOrg(
|
||||
blogURL,
|
||||
title,
|
||||
postSEO,
|
||||
postURL,
|
||||
image,
|
||||
description
|
||||
)
|
||||
|
||||
schema = JSON.stringify(schema)
|
||||
// const schema = createSchemaOrg(
|
||||
// blogURL,
|
||||
// title,
|
||||
// postSEO,
|
||||
// postURL,
|
||||
// image,
|
||||
// description,
|
||||
// author
|
||||
// )
|
||||
|
||||
return (
|
||||
<MetaTags
|
||||
description={description}
|
||||
image={image}
|
||||
url={url}
|
||||
schema={schema}
|
||||
// schema={(schema as unknown) as string}
|
||||
postSEO={postSEO}
|
||||
title={title}
|
||||
/>
|
||||
|
@ -1,5 +1,5 @@
|
||||
import React from 'react'
|
||||
import Helmet from 'react-helmet'
|
||||
import { Helmet } from 'react-helmet'
|
||||
import { useSiteMetadata } from '../../hooks/use-site-metadata'
|
||||
|
||||
const TypekitScript = (typekitID: string) => (
|
||||
|
@ -1,5 +1,5 @@
|
||||
import React, { useState } from 'react'
|
||||
import Helmet from 'react-helmet'
|
||||
import { Helmet } from 'react-helmet'
|
||||
import { Link } from 'gatsby'
|
||||
import Hamburger from '../atoms/Hamburger'
|
||||
import styles from './Menu.module.scss'
|
||||
|
@ -30,13 +30,7 @@ export default function Vcard() {
|
||||
|
||||
return (
|
||||
<div className={styles.vcard}>
|
||||
<Img
|
||||
className={styles.avatar}
|
||||
fixed={avatar}
|
||||
alt="avatar"
|
||||
width="80"
|
||||
height="80"
|
||||
/>
|
||||
<Img className={styles.avatar} fixed={avatar} alt="avatar" />
|
||||
<p className={styles.description}>
|
||||
Blog of designer & developer{' '}
|
||||
<a className="fn" rel="author" href={uri}>
|
||||
|
@ -3,7 +3,6 @@ import { graphql, Link } from 'gatsby'
|
||||
import PostImage from '../components/Post/PostImage'
|
||||
import Page from '../templates/Page'
|
||||
import styles from './goodies.module.scss'
|
||||
import { FluidObject } from 'gatsby-image'
|
||||
|
||||
const page = {
|
||||
frontmatter: {
|
||||
@ -13,42 +12,43 @@ const page = {
|
||||
}
|
||||
}
|
||||
|
||||
interface GoodieNode {
|
||||
interface Post {
|
||||
id: string
|
||||
fields: { slug: string }
|
||||
frontmatter: {
|
||||
title: string
|
||||
image: { childImageSharp: { fluid: FluidObject } }
|
||||
image: { childImageSharp: any }
|
||||
}
|
||||
}
|
||||
|
||||
const GoodiesThumbs = ({ edges }: { edges: [{ node: GoodieNode }] }) =>
|
||||
edges.map(({ node }: { node: GoodieNode }) => {
|
||||
const { title, image } = node.frontmatter
|
||||
const { slug } = node.fields
|
||||
const GoodiesThumb = ({ post }: { post: Post }) => {
|
||||
const { title, image } = post.frontmatter
|
||||
const { slug } = post.fields
|
||||
|
||||
return (
|
||||
<article className={styles.goodie} key={node.id}>
|
||||
{image && (
|
||||
<Link to={slug}>
|
||||
<h1 className={styles.title}>{title}</h1>
|
||||
<PostImage fluid={image.childImageSharp.fluid} alt={title} />
|
||||
</Link>
|
||||
)}
|
||||
</article>
|
||||
)
|
||||
})
|
||||
return (
|
||||
<article className={styles.goodie}>
|
||||
{image && (
|
||||
<Link to={slug}>
|
||||
<h1 className={styles.title}>{title}</h1>
|
||||
<PostImage fluid={image.childImageSharp.fluid} alt={title} />
|
||||
</Link>
|
||||
)}
|
||||
</article>
|
||||
)
|
||||
}
|
||||
|
||||
export default function Goodies({
|
||||
data,
|
||||
location
|
||||
}: {
|
||||
data: { goodies: { edges: [{ node: GoodieNode }] } }
|
||||
data: { goodies: { edges: [{ node: Post }] } }
|
||||
location: Location
|
||||
}) {
|
||||
return (
|
||||
<Page title={page.frontmatter.title} post={page} location={location}>
|
||||
<GoodiesThumbs edges={data.goodies.edges} />
|
||||
{data.goodies.edges.map(({ node }) => (
|
||||
<GoodiesThumb key={node.id} post={node} />
|
||||
))}
|
||||
</Page>
|
||||
)
|
||||
}
|
||||
|
@ -1,6 +1,5 @@
|
||||
import React from 'react'
|
||||
import { graphql, Link } from 'gatsby'
|
||||
import { FluidObject } from 'gatsby-image'
|
||||
import Page from '../templates/Page'
|
||||
import PostImage from '../components/Post/PostImage'
|
||||
import styles from './photos.module.scss'
|
||||
@ -12,43 +11,47 @@ const page = {
|
||||
}
|
||||
}
|
||||
|
||||
interface PhotoNode {
|
||||
node: {
|
||||
id: string
|
||||
fields: { slug: string }
|
||||
frontmatter: {
|
||||
title: string
|
||||
type: string
|
||||
image: { childImageSharp: { fluid: FluidObject } }
|
||||
}
|
||||
interface Photo {
|
||||
id: string
|
||||
fields: { slug: string }
|
||||
frontmatter: {
|
||||
title: string
|
||||
type: string
|
||||
image: { childImageSharp: any }
|
||||
}
|
||||
}
|
||||
|
||||
const PhotoThumbs = ({ edges }: { edges: PhotoNode[] }) =>
|
||||
edges.map(({ node }) => {
|
||||
const { title, image } = node.frontmatter
|
||||
const { slug } = node.fields
|
||||
const PhotoThumb = ({ photo }: { photo: Photo }) => {
|
||||
const { title, image } = photo.frontmatter
|
||||
const { slug } = photo.fields
|
||||
const { fluid } = image.childImageSharp
|
||||
|
||||
return (
|
||||
<article className={styles.photo} key={node.id}>
|
||||
{image && (
|
||||
<Link to={slug}>
|
||||
<PostImage
|
||||
title={title}
|
||||
fluid={image.childImageSharp.fluid}
|
||||
alt={title}
|
||||
/>
|
||||
</Link>
|
||||
)}
|
||||
</article>
|
||||
)
|
||||
})
|
||||
return (
|
||||
<article className={styles.photo}>
|
||||
{image && (
|
||||
<Link to={slug}>
|
||||
<PostImage title={title} fluid={fluid} alt={title} />
|
||||
</Link>
|
||||
)}
|
||||
</article>
|
||||
)
|
||||
}
|
||||
|
||||
interface PhotosData {
|
||||
photos: {
|
||||
edges: [
|
||||
{
|
||||
node: Photo
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
export default function Photos({
|
||||
data,
|
||||
location
|
||||
}: {
|
||||
data: { photos: { edges: PhotoNode[] } }
|
||||
data: PhotosData
|
||||
location: Location
|
||||
}) {
|
||||
return (
|
||||
@ -58,7 +61,9 @@ export default function Photos({
|
||||
location={location}
|
||||
section={styles.photos}
|
||||
>
|
||||
<PhotoThumbs edges={data.photos.edges} />
|
||||
{data.photos.edges.map(({ node }) => (
|
||||
<PhotoThumb key={node.id} photo={node} />
|
||||
))}
|
||||
</Page>
|
||||
)
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
import React from 'react'
|
||||
import Helmet from 'react-helmet'
|
||||
import { Helmet } from 'react-helmet'
|
||||
import SEO from '../components/atoms/SEO'
|
||||
import Layout from '../components/Layout'
|
||||
import styles from './Page.module.scss'
|
||||
|
@ -1,5 +1,5 @@
|
||||
import React from 'react'
|
||||
import Helmet from 'react-helmet'
|
||||
import { Helmet } from 'react-helmet'
|
||||
import { graphql } from 'gatsby'
|
||||
import Layout from '../components/Layout'
|
||||
import PostImage from '../components/Post/PostImage'
|
||||
|
@ -1,18 +1,16 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"outDir": "./dist/",
|
||||
"sourceMap": true,
|
||||
"noImplicitAny": true,
|
||||
"module": "commonjs",
|
||||
"target": "esnext",
|
||||
"jsx": "preserve",
|
||||
"lib": ["dom", "es2015", "es2017"],
|
||||
"strict": true,
|
||||
"noEmit": true,
|
||||
"isolatedModules": true,
|
||||
"jsx": "react",
|
||||
"lib": ["dom", "esnext"],
|
||||
"allowSyntheticDefaultImports": true,
|
||||
"esModuleInterop": true,
|
||||
"skipLibCheck": true,
|
||||
"noUnusedLocals": true,
|
||||
"noUnusedParameters": true,
|
||||
"preserveConstEnums": true
|
||||
"allowJs": true
|
||||
},
|
||||
"exclude": ["node_modules", "public", ".cache", "*.js"],
|
||||
"include": ["./src/**/*"]
|
||||
"include": ["./src/**/*", "./jest/**/*"]
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user