1509ae1952861e52c35161e0102c545eb4d45242eDiego Garciapackage com.xtremelabs.robolectric.shadows;
2509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
3509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport java.util.Arrays;
4509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport java.util.HashMap;
5509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport java.util.List;
6509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
7509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport android.content.UriMatcher;
8509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport android.net.Uri;
9509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
10509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport com.xtremelabs.robolectric.internal.Implementation;
11509ae1952861e52c35161e0102c545eb4d45242eDiego Garciaimport com.xtremelabs.robolectric.internal.Implements;
12509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
13509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia@Implements(UriMatcher.class)
14509ae1952861e52c35161e0102c545eb4d45242eDiego Garciapublic class ShadowUriMatcher {
15509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
16509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	public static class MatchNode {
17509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		public int code = UriMatcher.NO_MATCH;
18509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		public HashMap<String, MatchNode> map = new HashMap<String, ShadowUriMatcher.MatchNode>();
19509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		public MatchNode number;
20509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		public MatchNode text;
21509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
22509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		public MatchNode(int code) {
23509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			this.code = code;
24509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
25509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	}
26509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
27509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	public MatchNode rootNode;
28509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
29509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	public void __constructor__(int code) {
30509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		rootNode = new MatchNode(code);
31509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	}
32509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
33509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	@Implementation
34509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	public void addURI(String authority, String path, int code) {
35509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		MatchNode authNode = rootNode.map.get(authority);
36509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (authNode == null) {
37509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			authNode = new MatchNode(rootNode.code);
38509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			rootNode.map.put(authority, authNode);
39509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
40509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
41509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		String[] segments = path.split("/");
42509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		addNodes(authNode, Arrays.asList(segments), code);
43509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	}
44509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
45509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	@Implementation
46509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	public int match(Uri uri) {
47509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		String auth = uri.getAuthority();
48509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		List<String> segments = uri.getPathSegments();
49509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
50509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (!rootNode.map.containsKey(auth)) {
51509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			return rootNode.code;
52509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
53509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
54509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		return matchSegments(rootNode.map.get(auth), segments);
55509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	}
56509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
57509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	private int matchSegments(MatchNode node, List<String> segments) {
58509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (segments.isEmpty()) return node.code;
59509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		String segment = segments.get(0);
60509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		segments = segments.subList(1, segments.size());
61509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
62509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (node.map.containsKey(segment)) {
63509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			return matchSegments(node.map.get(segment), segments);
64509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
65509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (node.number != null) {
66509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			long id;
67509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			try {
68509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				id = Long.parseLong(segment);
69509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				if (id >= 0) {
70509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia					return matchSegments(node.number, segments);
71509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				}
72509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			}
73509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			catch (NumberFormatException e) {}
74509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
75509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (node.text != null) {
76509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			return matchSegments(node.text, segments);
77509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
78509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
79509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		return rootNode.code;
80509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	}
81509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
82509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	private void addNodes(MatchNode baseNode, List<String> segments, int code) {
83509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		MatchNode nextNode = null;
84509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		String segment = segments.get(0);
85509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
86509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (segment.equals("#")) {
87509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			nextNode = baseNode.number;
88509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			if (nextNode == null) {
89509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				nextNode = new MatchNode(rootNode.code);
90509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				baseNode.number = nextNode;
91509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			}
92509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
93509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		else if (segment.equals("*")) {
94509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			nextNode = baseNode.text;
95509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			if (nextNode == null) {
96509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				nextNode = new MatchNode(rootNode.code);
97509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				baseNode.text = nextNode;
98509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			}
99509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
100509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		else {
101509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			nextNode = baseNode.map.get(segment);
102509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			if (nextNode == null) {
103509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				nextNode = new MatchNode(rootNode.code);
104509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia				baseNode.map.put(segment, nextNode);
105509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			}
106509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
107509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
108509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		if (segments.size() > 1) {
109509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			addNodes(nextNode, segments.subList(1, segments.size()), code);
110509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
111509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		else {
112509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia			nextNode.code = code;
113509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia		}
114509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia	}
115509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia
116509ae1952861e52c35161e0102c545eb4d45242eDiego Garcia}
117