|
19 | 19 | # 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. |
20 | 20 | # |
21 | 21 |
|
| 22 | +import contextlib |
22 | 23 | import contextlib |
23 | 24 | import datetime |
24 | 25 | import os.path |
@@ -387,12 +388,27 @@ def test_getnextfile(self) -> None: |
387 | 388 |
|
388 | 389 | def test_save_ringtone_permissions(self) -> None: |
389 | 390 | """Test that SaveRingtone creates files with restrictive permissions.""" |
390 | | - # Create a simple ringtone dictionary |
391 | | - ringtone = {"Name": "Test", "Notes": [{"Note": "C", "Duration": 4, "Scale": 1}]} |
| 391 | + # Create a complete ringtone dictionary with all required fields |
| 392 | + ringtone = { |
| 393 | + "Name": "TestRingtone", |
| 394 | + "Notes": [ |
| 395 | + { |
| 396 | + "Type": "Note", |
| 397 | + "Value": 113, # Note value |
| 398 | + "Tempo": 120, |
| 399 | + "Scale": 1, |
| 400 | + "Style": "Natural", |
| 401 | + "Note": "C", |
| 402 | + "Duration": "1/4", |
| 403 | + "DurationSpec": "NoSpecialDuration", |
| 404 | + } |
| 405 | + ], |
| 406 | + } |
392 | 407 |
|
393 | | - # Create a unique temporary file path using a secure method |
394 | | - # We need to close and delete it so SaveRingtone can create it |
395 | | - with tempfile.NamedTemporaryFile(mode="wb", delete=False, suffix=".rttl") as f: |
| 408 | + # Test 1: Save using string filename |
| 409 | + with tempfile.NamedTemporaryFile( |
| 410 | + mode="wb", delete=False, suffix=".rttl" |
| 411 | + ) as f: |
396 | 412 | temp_file = f.name |
397 | 413 | os.unlink(temp_file) # Remove it so SaveRingtone can create it fresh |
398 | 414 |
|
@@ -430,6 +446,33 @@ def test_save_ringtone_permissions(self) -> None: |
430 | 446 | with contextlib.suppress(FileNotFoundError): |
431 | 447 | os.unlink(temp_file) |
432 | 448 |
|
| 449 | + # Test 2: Test multiple formats to ensure comprehensive coverage |
| 450 | + formats_to_test = ["rttl", "ott", "imy"] |
| 451 | + for fmt in formats_to_test: |
| 452 | + with tempfile.NamedTemporaryFile( |
| 453 | + mode="wb", delete=False, suffix=f".{fmt}" |
| 454 | + ) as f: |
| 455 | + temp_file = f.name |
| 456 | + os.unlink(temp_file) |
| 457 | + |
| 458 | + try: |
| 459 | + gammu.SaveRingtone(temp_file, ringtone, fmt) |
| 460 | + assert os.path.exists(temp_file), f"File not created for format {fmt}" |
| 461 | + |
| 462 | + # Verify permissions for each format |
| 463 | + if platform.system() != "Windows": |
| 464 | + file_stat = os.stat(temp_file) |
| 465 | + file_mode = stat.S_IMODE(file_stat.st_mode) |
| 466 | + assert (file_mode & stat.S_IRWXG) == 0, ( |
| 467 | + f"Format {fmt}: Group has permissions" |
| 468 | + ) |
| 469 | + assert (file_mode & stat.S_IRWXO) == 0, ( |
| 470 | + f"Format {fmt}: Others have permissions" |
| 471 | + ) |
| 472 | + finally: |
| 473 | + with contextlib.suppress(FileNotFoundError): |
| 474 | + os.unlink(temp_file) |
| 475 | + |
433 | 476 | def test_incoming_call(self) -> None: |
434 | 477 | self.check_incoming_call() |
435 | 478 | self._called = False |
|
0 commit comments