xref: /aosp_15_r20/external/skia/infra/bots/test_utils.py (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
1*c8dee2aaSAndroid Build Coastguard Worker#!/usr/bin/env python
2*c8dee2aaSAndroid Build Coastguard Worker#
3*c8dee2aaSAndroid Build Coastguard Worker# Copyright 2016 Google Inc.
4*c8dee2aaSAndroid Build Coastguard Worker#
5*c8dee2aaSAndroid Build Coastguard Worker# Use of this source code is governed by a BSD-style license that can be
6*c8dee2aaSAndroid Build Coastguard Worker# found in the LICENSE file.
7*c8dee2aaSAndroid Build Coastguard Worker
8*c8dee2aaSAndroid Build Coastguard Worker
9*c8dee2aaSAndroid Build Coastguard Worker"""Test utilities."""
10*c8dee2aaSAndroid Build Coastguard Worker
11*c8dee2aaSAndroid Build Coastguard Worker
12*c8dee2aaSAndroid Build Coastguard Workerimport filecmp
13*c8dee2aaSAndroid Build Coastguard Workerimport os
14*c8dee2aaSAndroid Build Coastguard Workerimport uuid
15*c8dee2aaSAndroid Build Coastguard Worker
16*c8dee2aaSAndroid Build Coastguard Worker
17*c8dee2aaSAndroid Build Coastguard Workerclass FileWriter(object):
18*c8dee2aaSAndroid Build Coastguard Worker  """Write files into a given directory."""
19*c8dee2aaSAndroid Build Coastguard Worker  def __init__(self, cwd):
20*c8dee2aaSAndroid Build Coastguard Worker    self._cwd = cwd
21*c8dee2aaSAndroid Build Coastguard Worker    if not os.path.exists(self._cwd):
22*c8dee2aaSAndroid Build Coastguard Worker      os.makedirs(self._cwd)
23*c8dee2aaSAndroid Build Coastguard Worker
24*c8dee2aaSAndroid Build Coastguard Worker  def mkdir(self, dname, mode=0o755):
25*c8dee2aaSAndroid Build Coastguard Worker    """Create the given directory with the given mode."""
26*c8dee2aaSAndroid Build Coastguard Worker    dname = os.path.join(self._cwd, dname)
27*c8dee2aaSAndroid Build Coastguard Worker    os.mkdir(dname)
28*c8dee2aaSAndroid Build Coastguard Worker    os.chmod(dname, mode)
29*c8dee2aaSAndroid Build Coastguard Worker
30*c8dee2aaSAndroid Build Coastguard Worker  def write(self, fname, mode=0o640):
31*c8dee2aaSAndroid Build Coastguard Worker    """Write the file with the given mode and random contents."""
32*c8dee2aaSAndroid Build Coastguard Worker    fname = os.path.join(self._cwd, fname)
33*c8dee2aaSAndroid Build Coastguard Worker    with open(fname, 'w') as f:
34*c8dee2aaSAndroid Build Coastguard Worker      f.write(str(uuid.uuid4()))
35*c8dee2aaSAndroid Build Coastguard Worker    os.chmod(fname, mode)
36*c8dee2aaSAndroid Build Coastguard Worker
37*c8dee2aaSAndroid Build Coastguard Worker  def remove(self, fname):
38*c8dee2aaSAndroid Build Coastguard Worker    """Remove the file."""
39*c8dee2aaSAndroid Build Coastguard Worker    fname = os.path.join(self._cwd, fname)
40*c8dee2aaSAndroid Build Coastguard Worker    if os.path.isfile(fname):
41*c8dee2aaSAndroid Build Coastguard Worker      os.remove(fname)
42*c8dee2aaSAndroid Build Coastguard Worker    else:
43*c8dee2aaSAndroid Build Coastguard Worker      os.rmdir(fname)
44*c8dee2aaSAndroid Build Coastguard Worker
45*c8dee2aaSAndroid Build Coastguard Worker
46*c8dee2aaSAndroid Build Coastguard Workerdef compare_trees(test, a, b):
47*c8dee2aaSAndroid Build Coastguard Worker  """Compare two directory trees, assert if any differences."""
48*c8dee2aaSAndroid Build Coastguard Worker  def _cmp(prefix, dcmp):
49*c8dee2aaSAndroid Build Coastguard Worker    # Verify that the file and directory names are the same.
50*c8dee2aaSAndroid Build Coastguard Worker    test.assertEqual(len(dcmp.left_only), 0)
51*c8dee2aaSAndroid Build Coastguard Worker    test.assertEqual(len(dcmp.right_only), 0)
52*c8dee2aaSAndroid Build Coastguard Worker    test.assertEqual(len(dcmp.diff_files), 0)
53*c8dee2aaSAndroid Build Coastguard Worker    test.assertEqual(len(dcmp.funny_files), 0)
54*c8dee2aaSAndroid Build Coastguard Worker
55*c8dee2aaSAndroid Build Coastguard Worker    # Verify that the files are identical.
56*c8dee2aaSAndroid Build Coastguard Worker    for f in dcmp.common_files:
57*c8dee2aaSAndroid Build Coastguard Worker      pathA = os.path.join(a, prefix, f)
58*c8dee2aaSAndroid Build Coastguard Worker      pathB = os.path.join(b, prefix, f)
59*c8dee2aaSAndroid Build Coastguard Worker      test.assertTrue(filecmp.cmp(pathA, pathB, shallow=False))
60*c8dee2aaSAndroid Build Coastguard Worker      statA = os.stat(pathA)
61*c8dee2aaSAndroid Build Coastguard Worker      statB = os.stat(pathB)
62*c8dee2aaSAndroid Build Coastguard Worker      test.assertEqual(statA.st_mode, statB.st_mode)
63*c8dee2aaSAndroid Build Coastguard Worker      with open(pathA, 'rb') as f:
64*c8dee2aaSAndroid Build Coastguard Worker        contentsA = f.read()
65*c8dee2aaSAndroid Build Coastguard Worker      with open(pathB, 'rb') as f:
66*c8dee2aaSAndroid Build Coastguard Worker        contentsB = f.read()
67*c8dee2aaSAndroid Build Coastguard Worker      test.assertEqual(contentsA, contentsB)
68*c8dee2aaSAndroid Build Coastguard Worker
69*c8dee2aaSAndroid Build Coastguard Worker    # Recurse on subdirectories.
70*c8dee2aaSAndroid Build Coastguard Worker    for prefix, obj in dcmp.subdirs.items():
71*c8dee2aaSAndroid Build Coastguard Worker      _cmp(prefix, obj)
72*c8dee2aaSAndroid Build Coastguard Worker
73*c8dee2aaSAndroid Build Coastguard Worker  _cmp('', filecmp.dircmp(a, b))
74