1
1
mirror of https://github.com/primer/css.git synced 2025-01-03 03:34:16 +03:00

Merge pull request #793 from primer/release-12.4.0

Release 12.4.0
This commit is contained in:
simurai 2019-05-15 09:50:50 +09:00 committed by GitHub
commit f6dccec048
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
14 changed files with 358 additions and 6413 deletions

View File

@ -1,3 +1,22 @@
# 12.4.0
### :rocket: Enhancement
- More responsive border utilities [#775](https://github.com/primer/css/pull/775)
- Add `overflow: visible` utilities [#798](https://github.com/primer/css/pull/798)
- Add `yellow` color utilities that will replace `pending` [#737](https://github.com/primer/css/pull/737)
### :bug: Bug Fix
- Fix Ruby Sass compiler warnings by quoting keys in `$hue-maps` declaration [#794](https://github.com/primer/css/pull/794)
### :house: Internal
- Remove `test-all-modules` scripts and old monorepo test scripts [#795](https://github.com/primer/css/pull/795)
- Resolve all but one ([#796](https://github.com/primer/css/pull/796)) vulnerability in npm dev dependencies [#797](https://github.com/primer/css/pull/797)
### Committers
- [@broccolini](https://github.com/broccolini)
- [@shawnbot](https://github.com/shawnbot)
- [@simurai](https://github.com/simurai)
# 12.3.1
### 🐛 Bug Fix

6330
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -1,6 +1,6 @@
{
"name": "@primer/css",
"version": "12.3.1",
"version": "12.4.0",
"description": "Primer is the CSS framework that powers GitHub's front-end design. primer includes 23 packages that are grouped into 3 core meta-packages for easy install. Each package and meta-package is independently versioned and distributed via npm, so it's easy to include all or part of Primer within your own project.",
"homepage": "https://primer.style/css",
"author": "GitHub, Inc.",
@ -39,7 +39,6 @@
"start-storybook": "start-storybook -p 8001",
"build-storybook": "build-storybook -o .storybuild",
"test": "npm-run-all -s test-urls test-migrate",
"test-all-modules": "ava --verbose tests/test-*.js",
"test-urls": "node docs-test/urls.js",
"test-migrate": "script/test-migrate"
},
@ -50,21 +49,18 @@
"@primer/blueprints": "4.0.1",
"@primer/components": "12.0.1",
"@primer/next-pages": "0.0.3",
"@storybook/addon-viewport": "5.0.0",
"@storybook/react": "5.0.10",
"@storybook/addon-viewport": "5.0.11",
"@storybook/react": "5.0.11",
"@svgr/webpack": "2.4.1",
"@zeit/next-css": "^1.0.1",
"@zeit/next-css": "1.0.1",
"@zeit/next-sass": "^1.0.1",
"action-status": "0.1.1",
"autoprefixer": "9.4.7",
"ava": "^0.23.0",
"broken-link-checker": "^0.7.8",
"char-spinner": "^1.0.1",
"chroma-js": "^1.4.1",
"clipboard-copy-element": "^0.5.0",
"code-blocks": "^1.1.0",
"colorette": "^1.0.7",
"css-loader": "^0.28.4",
"css-loader": "1.0.0",
"cssstats": "3.3.0",
"details-dialog-element": "^1.4.0",
"eslint": "4.19.1",
@ -83,10 +79,6 @@
"klaw": "3.0.0",
"loader-utils": "^1.1.0",
"mdx-constant": "^0.1.0",
"metalsmith": "^2.3.0",
"metalsmith-filter": "^1.0.2",
"metalsmith-matters": "^1.2.0",
"metalsmith-watch": "^1.0.3",
"minimist": "1.2.0",
"next": "7.0.2",
"node-fetch": "2.4.0",

View File

@ -21,7 +21,7 @@ The default border utility applies a solid, 1px border, with a default gray colo
</div>
```
Borders can be applied to a specific edge or to the Y axis.
Borders can be applied to a specific edge or to the X and Y axes individually:
```html
<div class="d-flex mb-3">
@ -38,6 +38,9 @@ Borders can be applied to a specific edge or to the Y axis.
.border-right
</div>
</div>
<div class="border-x">
.border-x
</div>
<div class="border-y">
.border-y
</div>
@ -198,10 +201,18 @@ You can also add rounded corners to each edge (top, right, bottom, left) with th
## Responsive borders
Top, right, bottom, and left border utilities are can be used responsively to add or remove borders to an element at different screensizes.
You can adjust border widths on all sides or each side individually with responsive border utilities:
* `border-(sm|md|lg|xl)` adds borders on all sides at and above the breakpoint. The `border-(sm|md|lg|xl)` shorthand is also supported.
* `border-(sm|md|lg|xl)-0` removes borders from all sides at and above the breakpoint.
* `border-(sm|md|lg|xl)-(top|right|bottom|left)` adds a border on the given side at and above the breakpoint.
* `border-(sm|md|lg|xl)-(top|right|bottom|left)-0` the border from the given side at and above the breakpoint.
```html
<div class="border-top border-sm-right border-md-bottom border-lg-top-0">
.border-top-0
<div class="border-top border-sm-right border-md-bottom border-md-top-0">
.border-top
<span class="d-none d-sm-inline">.border-sm-right </span>
<span class="d-none d-md-inline">.border-md-bottom </span>
<span class="d-none d-lg-inline">.border-md-top-0 </span>
</div>
```

View File

@ -75,9 +75,16 @@ Background colors are most commonly used for filling large blocks of content or
</div>
<div class="col-9 float-left">
<div class="container-lg clearfix">
<div class="h4">.bg-yellow-light</div>
<code>{colors.yellow[2]}, $bg-yellow-light</code>
<Swatch className="bg-yellow-light" />
<div class="col-6 float-left">
<div class="h4">.bg-yellow-dark</div>
<code>{colors.yellow[7]}, $bg-yellow-dark</code>
<Swatch className="bg-yellow-dark border-right-0" />
</div>
<div class="col-6 float-left">
<div class="h4">.bg-yellow-light</div>
<code>{colors.yellow[2]}, $bg-yellow-light</code>
<Swatch className="bg-yellow-light" />
</div>
</div>
</div>
</div>
@ -173,6 +180,10 @@ You can set the color inheritance on an element by using the `text-inherit` clas
.text-orange-light on white
</div>
<span class="float-left text-red tooltipped tooltipped-n" aria-label="Does not meet accessibility standards"><%= octicon("alert") %></span>
<div class="text-yellow mb-2">
.text-yellow on white
</div>
<span class="float-left text-red tooltipped tooltipped-n" aria-label="Does not meet accessibility standards"><%= octicon("alert") %></span>
<div class="text-green mb-2 ml-4">
.text-green on white
</div>
@ -199,6 +210,9 @@ You can set the color inheritance on an element by using the `text-inherit` clas
<div class="bg-green-light mb-2">
.text-gray-dark on .bg-green-light
</div>
<div class="bg-yellow-dark mb-2">
.text-gray-dark on .bg-yellow-dark
</div>
<div class="bg-yellow mb-2">
.text-gray-dark on .bg-yellow
</div>

View File

@ -105,16 +105,18 @@ Hide utilities are able to be applied or changed per breakpoint using the follow
Adjust the visibility of an element with `.v-hidden` and `.v-visible`.
## Overflow
Adjust element overflow with `.overflow-hidden`, `.overflow-scroll`, and `.overflow-auto`. `.overflow-hidden` can also be used to create a new [block formatting context](https://developer.mozilla.org/en-US/docs/Web/Guide/CSS/Block_formatting_context) or clear floats.
Adjust element overflow with `.overflow-hidden`, `.overflow-scroll`, and `.overflow-auto`, or use `.overflow-visible` to undo the effects of CSS with overflow issues. `.overflow-hidden` can also be used to create a new [block formatting context](https://developer.mozilla.org/en-US/docs/Web/Guide/CSS/Block_formatting_context) or clear floats.
Overflow utilities can also target x- and y-axes independently via:
* `.overflow-x-auto`
* `.overflow-x-hidden`
* `.overflow-x-scroll`
* `.overflow-x-visible`
* `.overflow-y-auto`
* `.overflow-y-hidden`
* `.overflow-y-scroll`
* `.overflow-y-visible`
## Floats
Use `.float-left` and `.float-right` to set floats, and `.clearfix` to clear.

View File

@ -1,157 +0,0 @@
#!/usr/bin/env node
const spinner = require('char-spinner')
const {gray, green, yellow, red, bold} = require('colorette')
const {SiteChecker} = require('broken-link-checker')
const yargs = require('yargs')
.option('excluded-schemes', {type: String, alias: 's', default: ['dash-feed', 'mailto']})
.option('filter-level', {type: Number, alias: 'L', default: 3})
.option('max-sockets-per-host', {type: Number, alias: 'm', default: 1})
.option('verbose', {type: Boolean, alias: 'v', default: false})
const options = yargs.argv
const args = options._
const VERBOSE = options.verbose
const pages = []
const seen = new Set()
const excepted = new Map()
const OK = ' ✓ '
const NOT_OK = ' ✘ '
const TAG_LENGTH = 3
const URL = args[0]
if (URL) {
log(green('go!'), bold(URL))
} else {
log('err', 'you must provide a URL')
process.exit(1)
}
let page = {url: URL, links: []}
const exceptions = {
'GitHub private repo': url =>
[
// this is a list of known GitHub private repos
'https://github.com/github/accessibility',
'https://github.com/github/design',
'https://github.com/github/design-systems',
'https://github.com/github/github',
'https://github.com/github/sentinel'
].some(repo => url.startsWith(repo))
}
const checker = new SiteChecker(options, {
page(error, url) {
if (error) {
log(red('ERR'), `${url} (${error.code})`)
} else if (page) {
const {url, response, links = []} = page
const num = String(links.length).padEnd(TAG_LENGTH)
let message = `${bold(num)}${pages.length ? ' unique' : ''} links`
if (!VERBOSE) message = `${message} on ${yellow(url)}`
log(OK, message)
if (links.length) {
pages.push(page)
}
}
},
html(tree, robots, response, url) {
if (VERBOSE) log(yellow('get'), url)
page = {url, links: []}
},
junk(result) {
const url = result.url.resolved || result.url.original
if (!url || seen.has(url)) {
return
} else if (VERBOSE) {
log(' '.repeat(TAG_LENGTH), gray(`skip ${shorten(url)}`))
} else if (result.excluded && url.indexOf(URL) !== 0) {
log(yellow('---'), gray(`excluded: ${url}`))
}
seen.add(url)
},
link(result) {
const url = result.url.resolved || result.url.original
if (VERBOSE && !seen.has(url)) log(' + ', gray('link'), shorten(url))
for (const [reason, test] of Object.entries(exceptions)) {
if (test(url)) {
log(yellow('---'), gray(`skip ${url}`), yellow(reason))
excepted.set(url, reason)
seen.add(url)
return
}
}
if (!seen.has(url)) page.links.push(result)
seen.add(url)
},
end() {
const allBroken = []
for (const page of pages) {
const broken = page.links.filter(link => link.broken)
allBroken.push(...broken)
if (!broken.length && !VERBOSE) {
continue
} else {
const num = broken.length ? red(` ${broken.length}`.padEnd(TAG_LENGTH)) : green(' 0').padEnd(TAG_LENGTH)
log(bold(num), `broken links on ${bold(page.url)}`)
}
for (const link of page.links) {
if (!link.broken && !VERBOSE) continue
const tag = link.broken ? red(NOT_OK) : green(OK)
const reason = link.broken ? link.brokenReason.replace(/HTTP_/, '') : ''
const url = link.url.resolved || link.url.original
log(tag, shorten(url), yellow(reason))
link.source = url
link.reason = reason
}
log('')
}
if (excepted.size) {
log(yellow(OK), `Excepted ${excepted.size} links:`)
const exceptedURLs = Array.from(excepted.keys()).sort()
for (const url of exceptedURLs) {
log(yellow(OK), `${yellow(excepted.get(url))} ${gray(url)}`)
}
log('')
}
if (allBroken.length) {
log(red(NOT_OK), `${red(allBroken.length)} broken links:`)
for (const link of allBroken) {
log(red(NOT_OK), red(link.reason), link.url.original, gray('from'), shorten(link.source))
}
log('')
process.exitCode = 1
} else {
log(green(OK), bold('0'), 'broken links')
}
log('')
}
})
spinner()
checker.enqueue(URL)
checker.resume()
function log(tag, ...args) {
spinner.clear()
console.log(tag ? gray(`[${tag}]`) : '', ...args)
}
function shorten(url) {
return String(url).indexOf(URL) === 0 ? gray(URL) + (url.substr(URL.length) || '/') : url
}

View File

@ -232,12 +232,12 @@ $pinks: (
) !default;
$hue-maps: (
gray: $grays,
blue: $blues,
green: $greens,
yellow: $yellows,
orange: $oranges,
red: $reds,
purple: $purples,
pink: $pinks,
"gray": $grays,
"blue": $blues,
"green": $greens,
"yellow": $yellows,
"orange": $oranges,
"red": $reds,
"purple": $purples,
"pink": $pinks,
) !default;

View File

@ -29,8 +29,6 @@ $border-purple: $purple !default;
$border-red: $red !default;
$border-red-light: desaturate($red-300, 60%) !default;
$border-purple: $purple !default;
$border-yellow: desaturate($yellow-300, 60%) !default;
$border-gray-dark: $gray-300 !default;
@ -55,6 +53,7 @@ $bg-red-light: $red-100 !default;
$bg-white: $white !default;
$bg-yellow: $yellow-500 !default;
$bg-yellow-light: $yellow-200 !default;
$bg-yellow-dark: $yellow-700 !default;
// Text colors
$text-blue: $blue-500 !default;
@ -68,3 +67,4 @@ $text-purple: $purple !default;
$text-pink: $pink-500 !default;
$text-red: $red-600 !default;
$text-white: $white !default;
$text-yellow: $yellow-800 !default;

View File

@ -2,19 +2,25 @@
// stylelint-disable primer/selector-no-utility
// stylelint-disable block-opening-brace-space-before, comment-empty-line-before
/* Add a gray border on all sides */
/* Add a gray border on all edges */
.border { border: $border !important; }
/* Add a gray border to the left and right */
.border-x {
border-right: $border !important;
border-left: $border !important;
}
/* Add a gray border to the top and bottom */
.border-y {
border-top: $border !important;
border-bottom: $border !important;
}
/* Remove borders from all sides */
.border-0 { border: 0 !important; }
.border-dashed { border-style: dashed !important; }
/* Change the border style to dashed, in conjunction with another utility */
.border-dashed {
border-style: dashed !important;
}
$edges: (
top: (top-left, top-right),
@ -23,9 +29,14 @@ $edges: (
left: (bottom-left, top-left)
);
/* Responsive gray borders */
@each $breakpoint, $variant in $responsive-variants {
@include breakpoint($breakpoint) {
/* Add a gray border */
/* Add a gray border on all sides at/above this breakpoint */
.border#{$variant} { border: $border !important; }
/* Set the border width to 0 on all sides at/above this breakpoint */
.border#{$variant}-0 { border: 0 !important; }
/* Add a gray border to the top */
.border#{$variant}-top { border-top: $border !important; }
/* Add a gray border to the right */

View File

@ -2,6 +2,8 @@
// stylelint-disable primer/selector-no-utility
// stylelint-disable block-opening-brace-space-before, comment-empty-line-before
@warn ".text-pending and .bg-pending will be deprecated in 13.0.0. Use .text-yellow and .bg-yellow-dark instead";
// background colors
/* Set the background to $bg-white */
.bg-white { background-color: $bg-white !important; }
@ -27,6 +29,8 @@
.bg-yellow { background-color: $bg-yellow !important; }
/* Set the background to $bg-yellow-light */
.bg-yellow-light { background-color: $bg-yellow-light !important; }
/* Set the background to $bg-yellow-dark */
.bg-yellow-dark { background-color: $bg-yellow-dark !important; }
/* Set the background to $bg-purple */
.bg-purple { background-color: $bg-purple !important; }
/* Set the background to $bg-pink */
@ -61,6 +65,8 @@
.text-gray-dark { color: $text-gray-dark !important; }
/* Set the text color to $text-green */
.text-green { color: $text-green !important; }
/* Set the text color to $text-yellow */
.text-yellow { color: $text-yellow !important; }
/* Set the text color to $text-orange */
.text-orange { color: $text-orange !important; }
/* Set the text color to $text-orange-light */
@ -74,10 +80,10 @@
/* Set the text color to inherit */
.text-inherit { color: inherit !important; }
// Text states
// These can probably all be regular utilities
// Pending states
// This will be deprecated in the future, use .text-yellow instead
.text-pending { color: $yellow-800 !important; }
// Separate text and background colors in future to improve a11y
// This will be deprecated in the future, use .bg-yellow-dark instead
.bg-pending { color: $yellow-700 !important; }
// Link colors

View File

@ -36,17 +36,11 @@
.v-align-baseline { vertical-align: baseline !important; }
// Overflow utilities
.overflow-hidden { overflow: hidden !important; }
.overflow-x-hidden { overflow-x: hidden !important; }
.overflow-y-hidden { overflow-y: hidden !important; }
.overflow-auto { overflow: auto !important; }
.overflow-x-auto { overflow-x: auto !important; }
.overflow-y-auto { overflow-y: auto !important; }
.overflow-scroll { overflow: scroll !important; }
.overflow-x-scroll { overflow-x: scroll !important; }
.overflow-y-scroll { overflow-y: scroll !important; }
@each $overflow in (visible, hidden, auto, scroll) {
.overflow-#{$overflow} { overflow: $overflow !important; }
.overflow-x-#{$overflow} { overflow-x: $overflow !important; }
.overflow-y-#{$overflow} { overflow-y: $overflow !important; }
}
// Clear floats
/* Clear floats around the element */

View File

@ -1,95 +0,0 @@
const {join} = require('path')
const fse = require('fs-extra')
const globby = require('globby')
const test = require('ava')
const minimatch = require('minimatch')
const cwd = process.cwd()
const css = require(cwd)
const pkg = require(join(cwd, 'package.json'))
const unique = list => Array.from(new Set(list)).sort()
/*
* These are the regular expressions that match what we
* expect to be class name instances in the docs.
* Patterns should group the matched class name(s) such that:
*
* ```js
* const [, klass, ] = pattern.exec(content)
* ```
*/
const classPatterns = [
// HTML class attributes
/class="([^"]+)"/ig,
/:class ?=> "([^"]+)"/g,
/class: "([^"]+)"/g,
// assume that ERB helpers generate an element with the same class
/<%= (\w+)\b/g,
]
const whitelistClasses = (pkg.primer ? pkg.primer.class_whitelist || [] : [])
.concat('js*')
const isWhitelisted = klass => {
return whitelistClasses.some(glob => minimatch(klass, glob))
}
// Find unique selectors from the cssstats selector list
function uniqueSelectors(selectors) {
return unique(selectors.map(s => {
// split multi-selectors into last class used .foo .bar .baz
return s.split(' ').pop()
})
.filter(s => {
// only match exact class selectors
return s.match(/^\.[a-z\-_]+$/ig)
}))
}
// From the given glob sources array, read the files and return found classnames
function getDocumentedClassnames(sources) {
return globby(sources)
.then(paths => {
return Promise.all(paths.map(path => {
return fse.readFile(path, 'utf8')
.then(content => ({path, content}))
}))
})
.then(files => {
return files.reduce((classes, {path, content}) => {
classPatterns.forEach(pattern => {
let match
while (match = pattern.exec(content)) {
// get the matched classnames and split by whitespace into classes
let klasses = match[1].trim().split(/\s+/)
classes.push(...klasses)
}
})
return classes
}, [])
})
.then(classes => unique(classes))
}
const selectors = uniqueSelectors(css.cssstats.selectors.values)
let classnames
test.before(t => {
return getDocumentedClassnames([
'docs/*.md',
'README.md'
])
.then(_ => (classnames = _))
})
selectors.forEach(selector => {
const klass = selector.replace(/^\./, '')
test(`Selector "${selector}" is documented/whitelisted`, t => {
t.plan(1)
if (isWhitelisted(klass)) {
t.pass(`Selector "${selector}" is whitelisted`)
} else {
t.is(classnames.includes(klass), true, `Selector "${selector}" is not documented`)
}
})
})

View File

@ -1,38 +0,0 @@
const test = require('ava')
const fs = require('fs-extra')
const globby = require('globby')
const {join} = require('path')
const {packages} = require('../lerna.json')
const year = (new Date()).getFullYear()
const yearRegex = new RegExp(`Copyright \\(c\\) ${year} GitHub Inc\\.`)
test(`LICENSE files have the current year ${year}`, t => {
return getPackageGlobs('LICENSE')
.then(paths => {
t.plan(paths.length)
return paths.map(path => {
const license = fs.readFileSync(path, 'utf8')
return t.regex(license, yearRegex, `The license "${path}" does not include the current year ${year}`)
})
})
})
test(`Source header copyrights have the current year ${year}`, t => {
return getPackageGlobs('{*.scss,lib/**/*.scss}')
.then(paths => {
t.plan(paths.length)
return paths.map(path => {
const source = fs.readFileSync(path, 'utf8')
if (source.match(/Copyright \(c\)/)) {
return t.regex(source, yearRegex, `The source's header "${path}" does not include the current year ${year}`)
} else {
return t.true(true)
}
})
})
})
function getPackageGlobs(glob) {
return globby(packages.map(pkg => join(pkg, glob)))
}