java regular expression check date format - java

private static String REGEX_ANY_MONTH = "January|Jan|February|Feb|March|Mar|April|Apr|May|June|Jun|"
+ "July|Jul|August|Aug|September|Sep|October|Oct|November|Nov|December|Dec";
private static String REGEX_ANY_YEAR = "[0-9]{4}";
private static String REGEX_ANY_DATE = "[0-9]{1,2}";
private String getFormat(String date) {
if (date.matches(REGEX_ANY_MONTH + " " + REGEX_ANY_DATE + "," + " " + REGEX_ANY_YEAR)) {
return "{MONTH} {DAY}, {YEAR}";
} else if (date.matches(REGEX_ANY_MONTH + " " + REGEX_ANY_YEAR)){
return "{MONTH} {YEAR}";
}
return null;
}
#Test
public void testGetFormatDateString() throws Exception{
String format = null;
String test = null;
test = "March 2012";
format = Whitebox.<String> invokeMethod(obj, "getFormat", test);
Assert.assertEquals("{MONTH} {YEAR}", format);
test = "March 10, 2012";
format = Whitebox.<String> invokeMethod(obj, "getFormat", test);
Assert.assertEquals("{MONTH} {DATE}, {YEAR}", format);
}
Both of the asserts are failing for me. What am I missing?

You need to wrap your piped list of month names in parentheses in order for it to match.
private static String REGEX_ANY_MONTH = "(January|Jan|February|Feb|March|Mar|April|Apr|May|June|Jun|"
+ "July|Jul|August|Aug|September|Sep|October|Oct|November|Nov|December|Dec)";
Otherwise the 'or' condition will be or-ing more than just the month.

Related

Remove some text between square brackets in Java 6

Would it be possible to change this:
[quote]user1 posted:
[quote]user2 posted:
Test1
[/quote]
Test2
[/quote]
Test3
to this:
Test3
Using Java 6?
ok, wrote some not regex solution.
String str ="[quote]user1 posted:[quote]user2 posted:Test1[/quote]Test2[/quote]Test3";
String startTag = "[quote]";
String endTag = "[/quote]";
String subStr;
int startTagIndex;
int endTagIndex;
while(str.contains(startTag) || str.contains(endTag)) {
startTagIndex = str.indexOf(startTag);
endTagIndex = str.indexOf(endTag) + endTag.length();
if(!str.contains(startTag)) {
startTagIndex = 0;
}
if(!str.contains(endTag)) {
endTagIndex = startTagIndex + startTag.length();
}
subStr = str.substring(startTagIndex, endTagIndex);;
str = str.replace(subStr, "");
}
I compiled this to Java 8. I don't believe I'm using any features not available in Java 6.
Edited: System.lineSeparator() was added in Java 1.7. I changed the line to
System.getProperty("line.separator").
public class RemoveQuotes {
public static void main(String[] args) {
String input = "[quote]user1 posted:\r\n" +
" [quote]user2 posted:\r\n" +
" Test1\r\n" +
" [/quote]\r\n" +
" Test2\r\n" +
"[/quote]\r\n" +
"Test3";
input = input.replace(System.getProperty("line.separator"), "");
String endQuote = "[/quote]";
int endPosition;
do {
int startPosition = input.indexOf("[quote]");
endPosition = input.lastIndexOf(endQuote);
if (endPosition >= 0) {
String output = input.substring(0, startPosition);
output += input.substring(endPosition + endQuote.length());
input = output;
}
} while (endPosition >= 0);
System.out.println(input);
}
}

regex join line infos

I have to parse this package:
WGS AUFFUELLUNGEN
ADMIN1 23.03.
17:09 -20- 1500.00
17:10 JD20 560.00
17:11 -2.0- 112.00
ADMIN1 24.03.
14:51 JD50 500.00
ADMIN2 27.03.
08:58 JD50 500.00
----------------------
3172.00
Parsing the user and date is easy:
\r?\n(.*)\s+(\d\d\.\d\d\.)
Parsing the time, denomination and amount is easy too:
\r?\n(\d\d:\d\d)\s+(.*)\s+(\d+\.\d\d)
But I need a parsing that detects user, date, time, denomination and amount for every booking at once.
Any ideas?
You will need some kind of intermediate structure you can iterate over. If you cant change your java code maybe you can use a regex to first match a whole block of you example string. In a second step you match all the details.
public class RegexTestCase {
private static final String PACKAGE
= "WGS AUFFUELLUNGEN \n" +
"ADMIN1 23.03.\n" +
"17:09 -20- 1500.00\n" +
"17:10 JD20 560.00\n" +
"17:11 -2.0- 112.00\n" +
"ADMIN1 24.03.\n" +
"14:51 JD50 500.00\n" +
"ADMIN2 27.03.\n" +
"08:58 JD50 500.00\n" +
"----------------------\n" +
" 3172.00\n";
private static final String NL = "\\r?\\n";
private static final String USER_DATE_REGEX
= "(.*?)\\s+(\\d\\d\\.\\d\\d\\.)";
private static final String TIME_AMOUNT_REGEX
= "(\\d\\d:\\d\\d)\\s+(.*?)\\s+(\\d+\\.\\d\\d)";
private static final String BLOCK_REGEX
= USER_DATE_REGEX + NL + "((" + TIME_AMOUNT_REGEX + NL + ")+)";
#Test
public void testRegex() throws Exception {
Pattern blockPattern = Pattern.compile( BLOCK_REGEX );
Pattern timeAmountPattern = Pattern.compile( TIME_AMOUNT_REGEX );
int count = 0;
Matcher blockMatcher = blockPattern.matcher( PACKAGE );
while (blockMatcher.find() ) {
String name = blockMatcher.group( 1 );
String date = blockMatcher.group( 2 );
String block = blockMatcher.group( 3 );
Matcher timeAmountMatcher = timeAmountPattern.matcher( block );
while ( timeAmountMatcher.find() ) {
String time = timeAmountMatcher.group( 1 );
String denom = timeAmountMatcher.group( 2 );
String amount = timeAmountMatcher.group( 3 );
assertEquals( "wrong name", RESULTS[count].name, name );
assertEquals( "wrong date", RESULTS[count].date, date );
assertEquals( "wrong time", RESULTS[count].time, time );
assertEquals( "wrong denom", RESULTS[count].denom, denom );
assertEquals( "wrong amount", RESULTS[count].amount, amount );
count++;
}
}
assertEquals( "wrong number of results", 5, count);
}
private static final Result[] RESULTS
= { new Result("ADMIN1", "23.03.", "17:09", "-20-", "1500.00")
, new Result("ADMIN1", "23.03.", "17:10", "JD20", "560.00")
, new Result("ADMIN1", "23.03.", "17:11", "-2.0-", "112.00")
, new Result("ADMIN1", "24.03.", "14:51", "JD50", "500.00")
, new Result("ADMIN2", "27.03.", "08:58", "JD50", "500.00")
};
static final class Result {
private final String name;
private final String date;
private final String time;
private final String denom;
private final String amount;
Result( String name, String date, String time, String denom, String amount ) {
this.name = name;
this.date = date;
this.time = time;
this.denom = denom;
this.amount = amount;
}
}
}
Your second regex is too eager, have a look at this.
I suggest to change it into \r?\n(\d\d:\d\d)\s+(.*?)\s+(\d+.\d\d)
This regex would match user, date, time, denomination and amount for every booking at once, but I have added the multiline regex flag.:
(^(.*)\s+(\d\d\.\d\d\.)$|^(\d\d:\d\d)\s+(.*)\s+(\d+\.\d\d)$)+
Split the entire string by new line
Iterate over the each line and
a. look for username and date by regex1, if matches then extract userName and Date
b. if regex1 doesn't, then look for time, denomincation and amount regex2 . if it matches
then extract time, denomination and amount from this.
final String userRegex = "^(\\w+)\\s+(\\d+\\.\\d+\\.)$";
final String timeRegex = "^(\\d+:\\d+)\\s+([\\S]+)\\s+(\\d+\\.?\\d+)$";
Sample Source:
public static void main(String[] args) {
final String userRegex = "^(\\w+)\\s+(\\d+\\.\\d+\\.)$";
final String timeRegex = "^(\\d+:\\d+)\\s+([\\S]+)\\s+(\\d+\\.?\\d+)$";
final String string = "WGS AUFFUELLUNGEN\n"
+ "ADMIN1 23.03.\n"
+ "17:09 -20- 1500.00\n"
+ "17:10 JD20 560.00\n"
+ "17:11 -2.0- 112.00\n"
+ "ADMIN1 24.03.\n"
+ "14:51 JD50 500.00\n"
+ "ADMIN2 27.03.\n"
+ "08:58 JD50 500.00\n"
+ "----------------------\n"
+ " 3172.00\n";
String[] list = string.split("\n");
Matcher m;
int cnt=1;
for (String s : list) {
m=Pattern.compile(userRegex).matcher(s);
if (m.matches()) {
System.out.println("##### List "+cnt+" ######");
System.out.println("User Name:"+m.group(1));
System.out.println("Date :"+m.group(2));
cnt++;
}
else
{
m=Pattern.compile(timeRegex).matcher(s);
if(m.matches())
{
System.out.println("Time :"+m.group(1));
System.out.println("Denomination :"+m.group(2));
System.out.println("Amount :"+m.group(3));
System.out.println("---------------------");
}
}
}
}

How to extract C,ST,L,O,OU,CN,E from X500Name in Java?

I'm using following code snippet to extract above details from a CSR file. Almost all the time I get correct values for COUNTRY, STATE, LOCALE, ORGANIZATION, ORGANIZATION_UNIT and COMMON_NAME but not for EMAIL.
public class CSRInfoDecoder {
private static Logger LOG = Logger.getLogger(CSRInfoDecoder.class.getName());
private static final String COUNTRY = "2.5.4.6";
private static final String STATE = "2.5.4.8";
private static final String LOCALE = "2.5.4.7";
private static final String ORGANIZATION = "2.5.4.10";
private static final String ORGANIZATION_UNIT = "2.5.4.11";
private static final String COMMON_NAME = "2.5.4.3";
private static final String EMAIL = "2.5.4.9";
private static final String csrPEM = "-----BEGIN CERTIFICATE REQUEST-----\n"
+ "MIICxDCCAawCAQAwfzELMAkGA1UEBhMCVVMxETAPBgNVBAgMCElsbGlub2lzMRAw\n"
+ "DgYDVQQHDAdDaGljYWdvMQ4wDAYDVQQKDAVDb2RhbDELMAkGA1UECwwCTkExDjAM\n"
+ "BgNVBAMMBUNvZGFsMR4wHAYJKoZIhvcNAQkBFg9rYmF4aUBjb2RhbC5jb20wggEi\n"
+ "MA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDSrEF27VvbGi5x7LnPk4hRigAW\n"
+ "1feGeKOmRpHd4j/kUcJZLh59NHJHg5FMF7u9YdZgnMdULawFVezJMLSJYJcCAdRR\n"
+ "hSN+skrQlB6f5wgdkbl6ZfNaMZn5NO1Ve76JppP4gl0rXHs2UkRJeb8lguOpJv9c\n"
+ "tw+Sn6B13j8jF/m/OhIYI8fWhpBYvDXukgADTloCjOIsAvRonkIpWS4d014deKEe\n"
+ "5rhYX67m3H7GtZ/KVtBKhg44ntvuT2fR/wB1FlDws+0gp4edlkDlDml1HXsf4FeC\n"
+ "ogijo6+C9ewC2anpqp9o0CSXM6BT2I0h41PcQPZ4EtAc4ctKSlzTwaH0H9MbAgMB\n"
+ "AAGgADANBgkqhkiG9w0BAQsFAAOCAQEAqfQbrxc6AtjymI3TjN2upSFJS57FqPSe\n"
+ "h1YqvtC8pThm7MeufQmK9Zd+Lk2qnW1RyBxpvWe647bv5HiQaOkGZH+oYNxs1XvM\n"
+ "y5huq+uFPT5StbxsAC9YPtvD28bTH7iXR1b/02AK2rEYT8a9/tCBCcTfaxMh5+fr\n"
+ "maJtj+YPHisjxKW55cqGbotI19cuwRogJBf+ZVE/4hJ5w/xzvfdKjNxTcNr1EyBE\n"
+ "8ueJil2Utd1EnVrWbmHQqnlAznLzC5CKCr1WfmnrDw0GjGg1U6YpjKBTc4MDBQ0T\n"
+ "56ZL2yaton18kgeoWQVgcbK4MXp1kySvdWq0Bc3pmeWSM9lr/ZNwNQ==\n"
+ "-----END CERTIFICATE REQUEST-----\n";
public static void main(String[] args) {
InputStream stream = new ByteArrayInputStream(csrPEM.getBytes(StandardCharsets.UTF_8));
CSRInfoDecoder m = new CSRInfoDecoder();
m.readCertificateSigningRequest(stream);
}
public void readCertificateSigningRequest(InputStream csrStream) {
PKCS10CertificationRequest csr = convertPemToPKCS10CertificationRequest(csrStream);
String compname = null;
if (csr == null) {
LOG.warn("FAIL! conversion of Pem To PKCS10 Certification Request");
} else {
X500Name x500Name = csr.getSubject();
System.out.println("x500Name is: " + x500Name + "\n");
System.out.println("COUNTRY: " + getX500Field(COUNTRY, x500Name));
System.out.println("STATE: " + getX500Field(STATE, x500Name));
System.out.println("LOCALE: " + getX500Field(LOCALE, x500Name));
System.out.println("ORGANIZATION: " + getX500Field(ORGANIZATION, x500Name));
System.out.println("ORGANIZATION_UNIT: " + getX500Field(ORGANIZATION_UNIT, x500Name));
System.out.println("COMMON_NAME: " + getX500Field(COMMON_NAME, x500Name));
System.out.println("EMAIL: " + getX500Field(EMAIL, x500Name));
}
}
Other than using ASN1ObjectIdentifiers, that is
private static final String COUNTRY = "2.5.4.6";
private static final String STATE = "2.5.4.8";
is there any other way that I can achieve this? I need to get value for each of these fields (C,ST,L,O,OU,CN,E) consistently.
I was able to achieve the above requirement by using following code snippet,
RDN email = x500Name.getRDNs(BCStyle.EmailAddress)[0];
RDN cn = x500Name.getRDNs(BCStyle.CN)[0];
System.out.println(email.getFirst().getValue().toString());
System.out.println(cn.getFirst().getValue().toString());
From this way I was able to get values for (C,ST,L,O,OU,CN,E) consistently.
For more information please refer to org.bouncycastle.asn1.x500.style.BCStyle;

Spark log parser with Java using regex

I'm trying to create a Java parser for a Spark log created with Log4J.
I wrote this code to recognize a starting task log-line but it doesn't work and I can't figure out why.
This is the regex:
public static final String datePattern = "\\d{4}\\-\\d{2}\\-\\d{2}";
public static final String timePattern = "\\d{2}\\:\\d{2}\\:\\d{2}\\,\\d{3}";
public static final String timeStampPattern = "(?<timeStamp>" + datePattern + "\\s" + timePattern + ")";
public static final String logLevelPattern = "(?<logLevel>\\w+)";
public static final String loggingClassPattern = "(?<loggingClass>\\w+:)";
public static final String taskUIdPattern = "(?<UIdPattern>\\d+)";
public static final String taskIdPattern = "\\d.\\d:\\d+";
public static final String taskStatusPattern = null;
public static final String endTaskLabelPattern = null;
public static final String stringPatternStartTask = timeStampPattern +
" " + logLevelPattern +
" " + loggingClassPattern +
" " + "Starting task" +
" " + taskIdPattern +
" " + "as TID" +
" " + taskUIdPattern +
"\\z";
This is the parsing attempt:
Pattern patternStartTask = Pattern.compile(stringPatternStartTask);
...
while((temp = br.readLine()) != null) {
if((m = patternStartTask.matcher(temp)).matches()) {
System.out.println(temp);
le = new StartTaskEvent();
}
...
if(m != null && le != null) {
le.setTaskId(m.group("taskId"));
le.setLogLevel(m.group("logLevel"));
le.setLoggingClass(m.group("loggingClass"));
le.setTimeStamp(sdf.parse(m.group("timeStamp")));
result.add(le);
}
}
The lines I'm trying to recognize are like this one:
2016-01-08 14:01:02 INFO TaskSetManager: Starting task 1.0:0 as TID 0 on executor 1
Your regex ends with:
" " + "as TID" +
" " + taskUIdPattern +
"\\z";
but in your string you have on executor 1 after taskUIdPattern, you have to add on executor 1 or, better, on executor \\d in your regex after taskUIdPattern

Java set the tommorrow id number to one

My requirements:
ddmm + 2numbers
dd - day
mm - month
number - id number
Examples of my output
Today - 031201, 031202, 031203 ...
Tommorrow - 041201
Properties file: (idNumber.properties)
idNumber = 1;
Here is the java code I did:
public class Test{
public static void main(String[] args)
{
Test test = new Test();
test.generate();
}
public String generate()
{
DateFormat dateFormat = new SimpleDateFormat("ddMM");
Date date = new Date();
String currentDate = dateFormat.format(date);
String idNumber = generateIdNumber();
String complete = currentDate + idNumber;
return complete;
}
public String generateIdNumber(){
Properties idNoProp = new Properties();
InputStream idNoInput = new FileInputStream("idNumber.properties"); //java properties file
idNoProp.load(idNoInput);
String idNumber = idNoProp.getProperty("idNumber");
int idNo = Integer.valueOf(idNumber);
String result = "";
if (idNo < 10) {
result = "0" + idNo;
} else {
result = "" + idNo;
}
idNo++;
OutputStream output = new FileOutputStream("idNumber.properties");
idNoProp.setProperty("idNumber", "" + idNo);
idNoProp.store(output, null);
return result;
}
}
My question is how do I reset the tommorrow id number start from 01?
You can add a property LAST_VISIT to your properties file. When you want to save the properties file, set the current date to it. In this way
DateFormat dateFormat = new SimpleDateFormat("ddMM");
Date date = new Date();
String currentDate = dateFormat.format(date);
idNoProp.setProperty("LAST_VISIT", currentDate);
Now in generateIdNumber() first check the value of LAST_VISIT. If it dose not equal currentDate , you must reset idNo. It works for everyday and every tommorow.
Try to put a class static field to remember last used date for ids. Whenever you are in the next date relatively to the field you'll reset your idNo and update the last used date field (sorry for spelling)
You can store a Map<String,Integer> that would hold the last index for each String representation of date. This way, each date would have its own indices starting with 1.
You can run a scheduler which will reset the idNo at the start of each day, like at 00 hours. This will always gives you the consistent result, as if sometimes server/program restarts, it will not lead to any duplicate result.
if you want format a number with two number, example '01' you could do this:
String.format("%02d", Integer.valueOf(idNumber));
instead of:
int idNo = Integer.valueOf(idNumber);
String result = "";
if (idNo < 10) {
result = "0" + idNo;
} else {
result = "" + idNo;
}
public class Test{
public static void main(String[] args) throws IOException
{
Test test = new Test();
System.out.println(""+test.generate());
}
public String generate() throws IOException
{
DateFormat dateFormat = new SimpleDateFormat("ddMM");
Date date = new Date();
String currentDate = dateFormat.format(date);
String idNumber = generateIdNumber(currentDate);
String complete = currentDate + idNumber;
return complete;
}
public String generateIdNumber(String currentDate) throws IOException{
Properties idNoProp = new Properties();
InputStream idNoInput = new FileInputStream("idNumber.properties"); //java properties file
idNoProp.load(idNoInput);
String idNumber = idNoProp.getProperty("idNumber");
int idNo = Integer.valueOf(idNumber);
String strOnlyDay = currentDate.substring(0, 2);
System.out.println(strOnlyDay);// will return the first two characters of the day
String result = "";
if (idNo < 10) {
result = "0" + idNo;
} else {
result = "" + idNo;
}
idNo++;
OutputStream output = new FileOutputStream("idNumber.properties");
if (strOnlyDay.equals("01")){
idNo = 1;
}
idNoProp.setProperty("idNumber", "" + idNo);
idNoProp.store(output, null);
return result;
}
}
Try to pass the value of your current date into generateIdNumber than see the code. I hope this will help. Hoping you will preserve the value of idNo.

Categories

Resources