Looking for a CSS Parser in java [closed]

2019-01-04 02:17发布

I'm looking for a CSS Parser in java. In particular my requirement is, for a given node/element in an HTML document, to be able to ask/get the css styles for that element from the Parser.

I know there is the W3C SAC interface and one or 2 implementations based on this - but turorials/examples appear non-existant.

Any help/points in right direction much appreciated.

Thanks

标签: java css parsing
8条回答
我只想做你的唯一
2楼-- · 2019-01-04 02:27

I've used CSSParser and I like it- it gives good feedback on errors as well.

Here's some sample code I've found and modified:

package com.dlogic;

import com.steadystate.css.parser.CSSOMParser;
import org.w3c.css.sac.InputSource;
import org.w3c.dom.css.CSSStyleSheet;
import org.w3c.dom.css.CSSRuleList;
import org.w3c.dom.css.CSSRule;
import org.w3c.dom.css.CSSStyleRule;
import org.w3c.dom.css.CSSStyleDeclaration;
import java.io.*;


public class CSSParserTest 
{

    protected static CSSParserTest oParser;

    public static void main(String[] args) {

            oParser = new CSSParserTest();

            if (oParser.Parse("design.css")) {

                System.out.println("Parsing completed OK");

            } else {

                System.out.println("Unable to parse CSS");

            }   
    }


     public boolean Parse(String cssfile) 
     {

         FileOutputStream out = null; 
         PrintStream ps = null; 
         boolean rtn = false;

         try
         {

                // cssfile accessed as a resource, so must be in the pkg (in src dir).
                InputStream stream = oParser.getClass().getResourceAsStream(cssfile);

                 // overwrites and existing file contents
                 out = new FileOutputStream("log.txt");

                 if (out != null)
                 {
                     //log file
                     ps = new PrintStream( out );
                     System.setErr(ps); //redirects stderr to the log file as well

                 } else {

                     return rtn; 

                }


                InputSource source = new InputSource(new InputStreamReader(stream));
                CSSOMParser parser = new CSSOMParser();
                // parse and create a stylesheet composition
                CSSStyleSheet stylesheet = parser.parseStyleSheet(source, null, null);

                //ANY ERRORS IN THE DOM WILL BE SENT TO STDERR HERE!!
                // now iterate through the dom and inspect.

                CSSRuleList ruleList = stylesheet.getCssRules();

                ps.println("Number of rules: " + ruleList.getLength());


               for (int i = 0; i < ruleList.getLength(); i++) 
               {
                 CSSRule rule = ruleList.item(i);
                 if (rule instanceof CSSStyleRule) 
                 {
                     CSSStyleRule styleRule=(CSSStyleRule)rule;
                     ps.println("selector:" + i + ": " + styleRule.getSelectorText());
                     CSSStyleDeclaration styleDeclaration = styleRule.getStyle();


                     for (int j = 0; j < styleDeclaration.getLength(); j++) 
                     {
                          String property = styleDeclaration.item(j);
                          ps.println("property: " + property);
                          ps.println("value: " + styleDeclaration.getPropertyCSSValue(property).getCssText());
                          ps.println("priority: " + styleDeclaration.getPropertyPriority(property));   
                     }



                  }// end of StyleRule instance test
                } // end of ruleList loop

               if (out != null) out.close();
               if (stream != null) stream.close();
               rtn = true;
            }
            catch (IOException ioe)
            {
                System.err.println ("IO Error: " + ioe);
            }
            catch (Exception e)
            {
                System.err.println ("Error: " + e);

            }
            finally
            {
                if (ps != null) ps.close(); 
            }

            return rtn;

    }

}
查看更多
Lonely孤独者°
3楼-- · 2019-01-04 02:27

I needed a CSS parser for an own project, but I found "CSSParser" to be too tedious and inflexible to work with (but that could have just been me), so I ended up writing my own simple but functional CSS parser.

Feel free to use it if you want to :-)

OSBCP CSS Parser

查看更多
在下西门庆
4楼-- · 2019-01-04 02:28

I just rolled out my own CSS Stream Parser for Java, available on github. What sets this parser apart includes:

  • It is a stream parser, so the parser handler will receive notification of all new content immediately after each item has been parsed
  • Full support for all currently-documented At-Rules
  • Custom classes TokenSequence and Token simplify processes for handling selectors, etc.
  • Easy to use and to understand
  • Useful for validation or for more advanced applications
  • Scalable: designed to be able to handle changes to CSS definitions.
查看更多
放荡不羁爱自由
5楼-- · 2019-01-04 02:31

A CSS library for reading and writing CSS2 and CSS3 files in Java is ph-css from https://github.com/phax/ph-css It is based on a JavaCC grammar and supports both CSS2 as well as CSS3 and additionally lets you parse HTML style attributes.

  • It supports the most common hacks "*", "_" and "$" which are not spec compliant
  • It supports CSS math - the calc() expression
  • It supports the @page rule
  • It supports the CSS3 media queries
  • It supports @viewport rules
  • It supports @keyframes rules
  • It supports @supports rules - quite new
  • It supports the @namespace rules
  • You can get source location information for the different elements (line + column number for start and end - both for the tag as well as for the complete construct)

Since May 21st, 2013 a JDK 1.5 version is also available, which makes it more interesting for Android development

查看更多
The star\"
6楼-- · 2019-01-04 02:37

jStyleParser provides exactly this functionality. It parses all the referenced style sheets and maps them to the DOM tree nodes.

查看更多
狗以群分
7楼-- · 2019-01-04 02:39

If you struggle with CSSParser, because there seems to be no documentation at all, and you perhaps want to parse just a CSS String, like value from style parameter, here is my simple sample of use:

import org.junit.Test;
import org.w3c.css.sac.InputSource;
import org.w3c.dom.css.CSSRule;
import org.w3c.dom.css.CSSStyleDeclaration;
import org.w3c.dom.css.CSSValue;

import com.steadystate.css.parser.CSSOMParser;

public class ParseCssTest {

@Test
public void testParseStyleDeclaration() throws IOException {
    String cssSample = "margin-top: 0cm; margin-bottom: 0cm; background: #e6e6e6";
    CSSOMParser parser = new CSSOMParser();
    CSSStyleDeclaration o = parser.parseStyleDeclaration(new InputSource(new StringReader(cssSample)));
    assertEquals("margin-top: 0cm; margin-bottom: 0cm; background: rgb(230, 230, 230)", o.toString());
    assertEquals("0cm", o.getPropertyCSSValue("margin-bottom").toString());
    assertEquals("0cm", o.getPropertyCSSValue("margin-bottom").getCssText());
    assertEquals(null, o.getPropertyCSSValue("foo"));
}

@Test
public void testParseARule() throws IOException {
    String cssSample = "r1 { margin-top: 0cm; margin-bottom: 0cm; background: #e6e6e6 }";
    CSSOMParser parser = new CSSOMParser();
    CSSRule o = parser.parseRule(new InputSource(new StringReader(cssSample)));
    assertEquals("r1 { margin-top: 0cm; margin-bottom: 0cm; background: rgb(230, 230, 230) }", o.toString());
}

@Test
public void parseStyleDeclarationWithAdvancedTests() throws IOException {
    String cssSample = "margin-top: 0 cm; margin-bottom: 0cm; background: #e6e6e6";
    CSSOMParser parser = new CSSOMParser();
    CSSStyleDeclaration o = parser.parseStyleDeclaration(new InputSource(new StringReader(cssSample)));
    assertEquals("margin-top: 0 cm; margin-bottom: 0cm; background: rgb(230, 230, 230)", o.toString());

    assertEquals("0cm", o.getPropertyCSSValue("margin-bottom").toString());
    assertEquals("0cm", o.getPropertyCSSValue("margin-bottom").getCssText());
    assertEquals(CSSValue.CSS_VALUE_LIST, o.getPropertyCSSValue("margin-top").getCssValueType());

    assertEquals("0 cm", o.getPropertyCSSValue("margin-top").toString());
    assertEquals("0 cm", o.getPropertyCSSValue("margin-top").getCssText());
    assertEquals(CSSValue.CSS_VALUE_LIST, o.getPropertyCSSValue("margin-top").getCssValueType());
}
}

Big advantage of CSSParser is that it is currently in Maven. So if you look for something rather simple and straightforwardly usable CSSParser seems to be good option.

Notes: it does automatic conversion for colors from hex format to rgb() format, but provides no help with sizes with units, it sees them as list of values! Not so good.

查看更多
登录 后发表回答