mirror of
https://github.com/kremalicious/portfolio.git
synced 2024-12-23 01:29:41 +01:00
Merge pull request #77 from kremalicious/feature/hostname
Hostname check
This commit is contained in:
commit
64c89d07a4
11
package.json
11
package.json
@ -9,6 +9,7 @@
|
||||
"author": "Matthias Kretschmann <m@kretschmann.io>",
|
||||
"scripts": {
|
||||
"start": "./node_modules/gatsby/dist/bin/gatsby.js develop",
|
||||
"ssr": "npm run build && serve -s public/",
|
||||
"lint:js": "eslint ./gatsby-*.js && eslint ./src/**/*.{js,jsx}",
|
||||
"lint:css": "stylelint ./src/**/*.{css,scss}",
|
||||
"lint": "npm run lint:js && npm run lint:css",
|
||||
@ -22,14 +23,14 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"file-saver": "^2.0.0",
|
||||
"gatsby": "^2.0.63",
|
||||
"gatsby": "^2.0.64",
|
||||
"gatsby-image": "^2.0.22",
|
||||
"gatsby-plugin-favicon": "^3.1.4",
|
||||
"gatsby-plugin-matomo": "^0.6.0",
|
||||
"gatsby-plugin-offline": "^2.0.18",
|
||||
"gatsby-plugin-offline": "^2.0.19",
|
||||
"gatsby-plugin-react-helmet": "^3.0.4",
|
||||
"gatsby-plugin-sass": "^2.0.7",
|
||||
"gatsby-plugin-sharp": "^2.0.14",
|
||||
"gatsby-plugin-sharp": "^2.0.15",
|
||||
"gatsby-plugin-sitemap": "^2.0.3",
|
||||
"gatsby-plugin-svgr": "^2.0.1",
|
||||
"gatsby-source-filesystem": "^2.0.11",
|
||||
@ -40,7 +41,7 @@
|
||||
"graphql": "^0.13.2",
|
||||
"intersection-observer": "^0.5.1",
|
||||
"js-yaml": "^3.12.0",
|
||||
"node-sass": "^4.10.0",
|
||||
"node-sass": "^4.11.0",
|
||||
"react": "^16.6.3",
|
||||
"react-dom": "^16.6.3",
|
||||
"react-helmet": "^5.2.0",
|
||||
@ -59,7 +60,7 @@
|
||||
"ava": "^0.25.0",
|
||||
"babel-eslint": "^10.0.1",
|
||||
"chrome-launcher": "^0.10.5",
|
||||
"eslint": "^5.9.0",
|
||||
"eslint": "^5.10.0",
|
||||
"eslint-config-prettier": "^3.3.0",
|
||||
"eslint-loader": "^2.1.1",
|
||||
"eslint-plugin-graphql": "^3.0.1",
|
||||
|
@ -3,6 +3,7 @@ import PropTypes from 'prop-types'
|
||||
import posed, { PoseGroup } from 'react-pose'
|
||||
import { fadeIn } from './atoms/Transitions'
|
||||
import Typekit from './atoms/Typekit'
|
||||
import HostnameCheck from './atoms/HostnameCheck'
|
||||
import Header from './organisms/Header'
|
||||
import Footer from './organisms/Footer'
|
||||
import styles from './Layout.module.scss'
|
||||
@ -29,6 +30,7 @@ export default class Layout extends PureComponent {
|
||||
return (
|
||||
<>
|
||||
<Typekit />
|
||||
<HostnameCheck />
|
||||
|
||||
<PoseGroup animateOnMount={true}>
|
||||
<RoutesContainer
|
||||
|
42
src/components/atoms/HostnameCheck.jsx
Normal file
42
src/components/atoms/HostnameCheck.jsx
Normal file
@ -0,0 +1,42 @@
|
||||
import React, { PureComponent } from 'react'
|
||||
import Helmet from 'react-helmet'
|
||||
import styles from './HostnameCheck.module.scss'
|
||||
|
||||
const allowedHosts = ['matthiaskretschmann.com', 'beta.matthiaskretschmann.com']
|
||||
|
||||
export default class HostnameInfo extends PureComponent {
|
||||
checkAllowedHost = () => {
|
||||
if (typeof window !== 'undefined' && window.location) {
|
||||
return allowedHosts.includes(window.location.hostname)
|
||||
}
|
||||
}
|
||||
|
||||
state = {
|
||||
// default to true so SSR builds never show the banner
|
||||
isAllowedHost: true
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
const isAllowedHost = this.checkAllowedHost()
|
||||
this.setState({ isAllowedHost })
|
||||
}
|
||||
|
||||
render() {
|
||||
// return nothing if we're on an allowed host
|
||||
if (this.state.isAllowedHost) return null
|
||||
|
||||
return (
|
||||
<>
|
||||
<Helmet>
|
||||
<meta name="robots" content="noindex,nofollow" />
|
||||
</Helmet>
|
||||
<aside className={styles.hostnameInfo}>
|
||||
<p>{`Hi there 👋. Please note that only the code and documentation of this
|
||||
site are open source. But my logo and the combination of typography,
|
||||
colors, and layout making up my brand identity are not. Don't just
|
||||
clone, do a remix.`}</p>
|
||||
</aside>
|
||||
</>
|
||||
)
|
||||
}
|
||||
}
|
22
src/components/atoms/HostnameCheck.module.scss
Normal file
22
src/components/atoms/HostnameCheck.module.scss
Normal file
@ -0,0 +1,22 @@
|
||||
@import 'variables';
|
||||
|
||||
.hostnameInfo {
|
||||
position: sticky;
|
||||
top: 0;
|
||||
z-index: 99;
|
||||
padding: $spacer / 3;
|
||||
font-size: $font-size-small;
|
||||
font-weight: bold;
|
||||
background: rgba($brand-light, .8);
|
||||
|
||||
:global(.dark) & {
|
||||
background: rgba($body-background-color--dark, .8);
|
||||
}
|
||||
|
||||
p {
|
||||
margin: auto;
|
||||
margin-bottom: 0;
|
||||
max-width: $screen-lg;
|
||||
text-align: center;
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
import React from 'react'
|
||||
import React, { PureComponent } from 'react'
|
||||
import { StaticQuery, graphql } from 'gatsby'
|
||||
import saveAs from 'file-saver'
|
||||
import vCard from 'vcf'
|
||||
@ -31,30 +31,34 @@ const query = graphql`
|
||||
}
|
||||
`
|
||||
|
||||
const Vcard = () => (
|
||||
<StaticQuery
|
||||
query={query}
|
||||
render={data => {
|
||||
const meta = data.dataYaml
|
||||
export default class Vcard extends PureComponent {
|
||||
render() {
|
||||
return (
|
||||
<StaticQuery
|
||||
query={query}
|
||||
render={data => {
|
||||
const meta = data.dataYaml
|
||||
|
||||
const handleAddressbookClick = e => {
|
||||
e.preventDefault()
|
||||
constructVcard(meta)
|
||||
}
|
||||
const handleAddressbookClick = e => {
|
||||
e.preventDefault()
|
||||
constructVcard(meta)
|
||||
}
|
||||
|
||||
return (
|
||||
<a
|
||||
// href is kinda fake, only there for usability
|
||||
// so user knows what to expect when hovering the link before clicking
|
||||
href={meta.addressbook}
|
||||
onClick={handleAddressbookClick}
|
||||
>
|
||||
Add to addressbook
|
||||
</a>
|
||||
)
|
||||
}}
|
||||
/>
|
||||
)
|
||||
return (
|
||||
<a
|
||||
// href is kinda fake, only there for usability
|
||||
// so user knows what to expect when hovering the link before clicking
|
||||
href={meta.addressbook}
|
||||
onClick={handleAddressbookClick}
|
||||
>
|
||||
Add to addressbook
|
||||
</a>
|
||||
)
|
||||
}}
|
||||
/>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
// Construct the download from a blob of the just constructed vCard,
|
||||
// and save it to user's file system
|
||||
@ -120,5 +124,3 @@ const toDataURL = (src, callback, outputFormat) => {
|
||||
img.src = src
|
||||
}
|
||||
}
|
||||
|
||||
export default Vcard
|
||||
|
Loading…
Reference in New Issue
Block a user