From d0a8a3b18ce00e20621d744e04d842b5cd1780fa Mon Sep 17 00:00:00 2001 From: Yorick Peterse Date: Sun, 5 Oct 2014 23:46:41 +0200 Subject: [PATCH] Basic support for parsing CSS pseudo classes. This currently does not yet allow chained pseudo classes, nor does it allow for pseudos such as nth-child(2n). --- lib/oga/css/parser.y | 31 +++++++++++++++++++--- spec/oga/css/parser/pseudo_classes_spec.rb | 18 +++++++++++++ 2 files changed, 46 insertions(+), 3 deletions(-) create mode 100644 spec/oga/css/parser/pseudo_classes_spec.rb diff --git a/lib/oga/css/parser.y b/lib/oga/css/parser.y index f42dc59..0e76563 100644 --- a/lib/oga/css/parser.y +++ b/lib/oga/css/parser.y @@ -14,6 +14,7 @@ rule path_member : node_test | axis + | pseudo_class ; path_members @@ -60,6 +61,11 @@ rule | op_members T_HYPHEN_IN op_members { s(:hyphen_in, val[0],val[2]) } ; + op_members + : node_test + | string + ; + axis # x > y : node_test T_CHILD node_test @@ -80,14 +86,33 @@ rule } ; - op_members - : node_test - | string + pseudo_class + # x:root + : node_test T_COLON T_IDENT { s(:pseudo, val[2], val[0]) } + + # x:nth-child(2) + | node_test T_COLON T_IDENT T_LPAREN pseudo_args T_RPAREN + { + s(:pseudo, val[2], val[0], *val[4]) + } + ; + + pseudo_args + : pseudo_args pseudo_arg { val[0] << val[1] } + | pseudo_arg { val } + ; + + pseudo_arg + : integer ; string : T_STRING { s(:string, val[0]) } ; + + integer + : T_INT { s(:int, val[0].to_i) } + ; end ---- inner diff --git a/spec/oga/css/parser/pseudo_classes_spec.rb b/spec/oga/css/parser/pseudo_classes_spec.rb new file mode 100644 index 0000000..386b8ae --- /dev/null +++ b/spec/oga/css/parser/pseudo_classes_spec.rb @@ -0,0 +1,18 @@ +require 'spec_helper' + +describe Oga::CSS::Parser do + context 'pseudo classes' do + example 'parse the :root pseudo class' do + parse_css('x:root').should == s(:pseudo, 'root', s(:test, nil, 'x')) + end + + example 'parse the :nth-child pseudo class' do + parse_css('x:nth-child(2)').should == s( + :pseudo, + 'nth-child', + s(:test, nil, 'x'), + s(:int, 2) + ) + end + end +end