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