package com.plectix.simulator.parser.util; import java.util.LinkedHashMap; import java.util.LinkedList; import java.util.List; import java.util.Map; import java.util.StringTokenizer; import com.plectix.simulator.parser.DocumentFormatException; import com.plectix.simulator.parser.IncompletesDisabledException; import com.plectix.simulator.parser.ParseErrorException; import com.plectix.simulator.parser.ParseErrorMessage; import com.plectix.simulator.parser.abstractmodel.ModelAgent; import com.plectix.simulator.parser.abstractmodel.ModelSite; import com.plectix.simulator.staticanalysis.LinkStatus; /** * It's not a factory, as a OOP-pattern, just named such */ public final class AgentFactory { private static final String PATTERN_AGENT_SITE = "^[0-9[a-zA-Z]]+[0-9[a-zA-Z]\\_\\^\\-]*"; private static final String PATTERN_STATE = "^[0-9[a-zA-Z]]+"; private static final String SYMBOL_CONNECTED_TRUE_VALUE = "_"; private final boolean allowIncompletes; public AgentFactory(boolean allowIncompletes) { this.allowIncompletes = allowIncompletes; } public final List<ModelAgent> parseAgent(String line) throws ParseErrorException, DocumentFormatException, IncompletesDisabledException { line = line.replaceAll("[ ]", ""); // if (!testLine(line)) // throw new ParseErrorException(); StringTokenizer st = new StringTokenizer(line, "),"); Map<Integer, ModelSite> map = new LinkedHashMap<Integer, ModelSite>(); StringTokenizer agent; String ccomp; String site; List<ModelAgent> listAgent = new LinkedList<ModelAgent>(); ModelAgent cagent = null; while (st.hasMoreTokens()) { ccomp = st.nextToken().trim(); if (ccomp.indexOf("(") != -1) { agent = new StringTokenizer(ccomp, "("); if (agent.countTokens() == 0) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_LINE, line); ccomp = agent.nextToken(); // Agent name. if (!ccomp.trim().matches(PATTERN_AGENT_SITE)) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_AGENT_NAME, ccomp); cagent = new ModelAgent(ccomp); listAgent.add(cagent); while (agent.hasMoreTokens()) { site = agent.nextToken().trim(); // Site name or State name. cagent.addCorrectSite(parseSite(site, map)); // <-------Agent } } else { if (cagent == null) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_AGENT_NAME, ccomp); cagent.addCorrectSite(parseSite(ccomp, map)); // <------Agent } } if (!map.isEmpty()) { throw new DocumentFormatException(ParseErrorMessage.BAD_CONNECTIONS_COORDINATION, line); } if (!AgentFormatChecker.check(line)) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_LINE, line); return listAgent; } private final ModelSite parseSite(String line, Map<Integer, ModelSite> connectionsData) throws ParseErrorException, IncompletesDisabledException { String state = null; String connect = null; SiteProperty dt = null; dt = parseLine(line, SitePropertyKey.INTERNAL_STATE); line = dt.getSiteLine(); state = dt.getPropertyLine(); if (state != null) { dt = parseLine(state, SitePropertyKey.CONNECTION); state = dt.getSiteLine(); if (!AgentFormatChecker.checkState(state)) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_INTERNAL_STATE, line); } else { dt = parseLine(line, SitePropertyKey.CONNECTION); line = dt.getSiteLine(); } connect = dt.getPropertyLine(); if (!line.trim().matches(PATTERN_AGENT_SITE)) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_SITE_NAME, line); final String siteName = line; if(siteName.contains("*")){ throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_SITE_NAME, line); } ModelSite csite = new ModelSite(siteName); if (state != null) if ((state.length() != 0) && state.trim().matches(PATTERN_STATE)) { csite.setInternalState(state); } else { throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_INTERNAL_STATE, line); } if (connect != null) if (connect.length() == 0) { if (!allowIncompletes) { throw new IncompletesDisabledException(ParseErrorMessage.INCOMPLETES_DISABLED, line); } csite.getLinkState().setStatusLink(LinkStatus.WILDCARD); } else if (connect.equals(SYMBOL_CONNECTED_TRUE_VALUE)) { if (! allowIncompletes) { throw new IncompletesDisabledException(ParseErrorMessage.INCOMPLETES_DISABLED, line); } csite.getLinkState().setStatusLink(LinkStatus.BOUND); } else { try { int index = Integer.valueOf(connect); ModelSite abstractSite = connectionsData.get(index); if (abstractSite != null) { abstractSite.getLinkState().setSite(csite); csite.getLinkState().setSite(abstractSite); abstractSite.setLinkIndex(index); csite.setLinkIndex(index); connectionsData.remove(index); } else { connectionsData.put(index, csite); } } catch (Exception e) { throw new ParseErrorException(ParseErrorMessage.CONNECTION_SYMBOL_EXPECTED, line); } } if (csite == null) throw new ParseErrorException(ParseErrorMessage.UNEXPECTED_LINE, line); return csite; } private final SiteProperty parseLine(String line, SitePropertyKey dividingSymbol) throws ParseErrorException { String id = dividingSymbol.getSymbol(); SiteProperty ds = new SiteProperty(line); int i = -1; switch (dividingSymbol) { case INTERNAL_STATE: { i = line.indexOf(id); break; } case CONNECTION: { i = line.indexOf(id); } case BLIND_CONNECTION: { if (i != -1) { id = SitePropertyKey.BLIND_CONNECTION.getSymbol(); i = line.indexOf(id); if (i == -1) { i = line.indexOf(SitePropertyKey.CONNECTION.getSymbol()); String test = new String(line); test = test.substring(i + 1); if (test.length() == 0) throw new ParseErrorException(ParseErrorMessage.CONNECTION_SYMBOL_EXPECTED, line); } break; } } case WILDCARD: { if (i == -1) { id = SitePropertyKey.WILDCARD.getSymbol(); i = line.indexOf(id); } break; } } if (i != -1) { String content = line.substring(i + 1).trim(); line = line.substring(0, i).trim(); ds.setSiteLine(line); ds.setPropertyLine(content); } return ds; } }