Complete Phase 5.1: Add terminator handling for nested control flow
Co-authored-by: moe-charm <217100418+moe-charm@users.noreply.github.com>
This commit is contained in:
@ -347,7 +347,9 @@ impl MirBuilder {
|
||||
self.current_block = Some(then_block);
|
||||
self.ensure_block_exists(then_block)?;
|
||||
let then_value = self.build_expression(then_branch)?;
|
||||
self.emit_instruction(MirInstruction::Jump { target: merge_block })?;
|
||||
if !self.is_current_block_terminated() {
|
||||
self.emit_instruction(MirInstruction::Jump { target: merge_block })?;
|
||||
}
|
||||
|
||||
// Build else branch
|
||||
self.current_block = Some(else_block);
|
||||
@ -363,7 +365,9 @@ impl MirBuilder {
|
||||
})?;
|
||||
void_val
|
||||
};
|
||||
self.emit_instruction(MirInstruction::Jump { target: merge_block })?;
|
||||
if !self.is_current_block_terminated() {
|
||||
self.emit_instruction(MirInstruction::Jump { target: merge_block })?;
|
||||
}
|
||||
|
||||
// Create merge block with phi function
|
||||
self.current_block = Some(merge_block);
|
||||
|
||||
@ -1,58 +0,0 @@
|
||||
// 🧪 新しいBoxタイプの統合テスト
|
||||
// Arc<Mutex>パターンが正しく動作することを確認
|
||||
|
||||
print("=== New Boxes Integration Test ===")
|
||||
|
||||
// 📦 ArrayBox Test
|
||||
print("\n🔹 ArrayBox Test:")
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
arr.push("Hello")
|
||||
arr.push("World")
|
||||
arr.push(42)
|
||||
print("Array length: " + arr.length())
|
||||
print("Array contents: " + arr.toString())
|
||||
|
||||
// 🗄️ MapBox Test
|
||||
print("\n🔹 MapBox Test:")
|
||||
local map
|
||||
map = new MapBox()
|
||||
map.set("name", "Alice")
|
||||
map.set("age", 25)
|
||||
map.set("active", true)
|
||||
print("Map size: " + map.size())
|
||||
print("Name: " + map.get("name"))
|
||||
print("Age: " + map.get("age"))
|
||||
print("Has email: " + map.has("email"))
|
||||
|
||||
// 📊 BufferBox Test
|
||||
print("\n🔹 BufferBox Test:")
|
||||
local buffer
|
||||
buffer = new BufferBox()
|
||||
local data_array
|
||||
data_array = new ArrayBox()
|
||||
data_array.push(72) // H
|
||||
data_array.push(101) // e
|
||||
data_array.push(108) // l
|
||||
data_array.push(108) // l
|
||||
data_array.push(111) // o
|
||||
buffer.write(data_array)
|
||||
print("Buffer size: " + buffer.length())
|
||||
|
||||
// 🔍 RegexBox Test
|
||||
print("\n🔹 RegexBox Test:")
|
||||
local regex
|
||||
regex = new RegexBox("[0-9]+")
|
||||
print("Regex pattern: " + regex.pattern())
|
||||
print("Test '123': " + regex.test("123"))
|
||||
print("Test 'abc': " + regex.test("abc"))
|
||||
|
||||
// ✅ ResultBox Test
|
||||
print("\n🔹 ResultBox Test:")
|
||||
local ok_result, err_result
|
||||
ok_result = new ResultBox()
|
||||
ok_result = ResultBox.ok("Success!")
|
||||
print("OK result: " + ok_result.toString())
|
||||
print("Is OK: " + ok_result.is_ok())
|
||||
|
||||
print("\n🎉 All Arc<Mutex> pattern tests completed successfully!")
|
||||
@ -1,74 +0,0 @@
|
||||
// ArrayBox実装テスト
|
||||
print("=== ArrayBox実装テスト ===")
|
||||
|
||||
// 1. ArrayBoxの作成
|
||||
print("\n1. ArrayBoxの作成:")
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
print("ArrayBox created: " + arr.toString())
|
||||
// print("Type: " + arr.type_name()) // type_nameはArrayBoxのメソッドではない
|
||||
print("Initial length: " + arr.length())
|
||||
|
||||
// 2. 要素の追加(push)
|
||||
print("\n2. 要素の追加:")
|
||||
arr.push("Apple")
|
||||
arr.push("Banana")
|
||||
arr.push("Cherry")
|
||||
arr.push(42)
|
||||
arr.push(true)
|
||||
print("After push: " + arr.toString())
|
||||
print("Length: " + arr.length())
|
||||
|
||||
// 3. 要素の取得(get)
|
||||
print("\n3. 要素の取得:")
|
||||
print("arr.get(0) = " + arr.get(0))
|
||||
print("arr.get(1) = " + arr.get(1))
|
||||
print("arr.get(3) = " + arr.get(3))
|
||||
print("arr.get(10) = " + arr.get(10)) // 範囲外
|
||||
|
||||
// 4. 要素の削除(pop)
|
||||
print("\n4. 要素の削除:")
|
||||
local popped
|
||||
popped = arr.pop()
|
||||
print("Popped: " + popped)
|
||||
print("After pop: " + arr.toString())
|
||||
print("Length: " + arr.length())
|
||||
|
||||
// 5. インデックス検索(indexOf)
|
||||
print("\n5. インデックス検索:")
|
||||
print("indexOf('Apple') = " + arr.indexOf("Apple"))
|
||||
print("indexOf('Banana') = " + arr.indexOf("Banana"))
|
||||
print("indexOf('NotExist') = " + arr.indexOf("NotExist"))
|
||||
|
||||
// 6. 要素の確認(contains)
|
||||
print("\n6. 要素の確認:")
|
||||
print("contains('Apple') = " + arr.contains("Apple"))
|
||||
print("contains(42) = " + arr.contains(42))
|
||||
print("contains('NotExist') = " + arr.contains("NotExist"))
|
||||
|
||||
// 7. 文字列結合(join)
|
||||
print("\n7. 文字列結合:")
|
||||
print("join(', ') = " + arr.join(", "))
|
||||
print("join(' - ') = " + arr.join(" - "))
|
||||
|
||||
// 8. 要素の設定(set)
|
||||
print("\n8. 要素の設定:")
|
||||
arr.set(1, "Orange")
|
||||
print("After set(1, 'Orange'): " + arr.toString())
|
||||
|
||||
// 9. 要素の削除(remove)
|
||||
print("\n9. 要素の削除:")
|
||||
local removed
|
||||
removed = arr.remove(2)
|
||||
print("Removed: " + removed)
|
||||
print("After remove(2): " + arr.toString())
|
||||
print("Length: " + arr.length())
|
||||
|
||||
// 10. 配列のクリア(clear)
|
||||
print("\n10. 配列のクリア:")
|
||||
arr.clear()
|
||||
print("After clear: " + arr.toString())
|
||||
print("Length: " + arr.length())
|
||||
print("isEmpty: " + arr.isEmpty())
|
||||
|
||||
print("\n=== ArrayBoxテスト完了! ===")
|
||||
@ -1,20 +0,0 @@
|
||||
// 🧪 ArrayBoxの簡単なテスト
|
||||
|
||||
print("=== ArrayBox Simple Test ===")
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
|
||||
// 基本的な操作
|
||||
arr.push("Hello")
|
||||
arr.push("World")
|
||||
print("Length: " + arr.length())
|
||||
print("Get 0: " + arr.get(0))
|
||||
print("Get 1: " + arr.get(1))
|
||||
|
||||
// pop
|
||||
local item
|
||||
item = arr.pop()
|
||||
print("Popped: " + item)
|
||||
print("Length after pop: " + arr.length())
|
||||
|
||||
print("Test completed!")
|
||||
@ -1,81 +0,0 @@
|
||||
// test_array_improvements.nyash - ArrayBox Phase 2 improvements test
|
||||
// Testing: sort(), reverse(), indexOf(), slice() methods
|
||||
|
||||
print("📦 Testing ArrayBox improvements...")
|
||||
|
||||
// Basic array creation and setup
|
||||
local arr, result, sliceResult
|
||||
|
||||
print("=== Setup: Creating test array ===")
|
||||
arr = new ArrayBox()
|
||||
arr.push(3)
|
||||
arr.push(1)
|
||||
arr.push(4)
|
||||
arr.push(1)
|
||||
arr.push(5)
|
||||
print("Original array: " + arr.toString())
|
||||
|
||||
print("\n=== Test 1: sort() method ===")
|
||||
arr.sort()
|
||||
print("After sort(): " + arr.toString())
|
||||
// Expected: [1, 1, 3, 4, 5]
|
||||
|
||||
print("\n=== Test 2: reverse() method ===")
|
||||
arr.reverse()
|
||||
print("After reverse(): " + arr.toString())
|
||||
// Expected: [5, 4, 3, 1, 1]
|
||||
|
||||
print("\n=== Test 3: indexOf() method ===")
|
||||
result = arr.indexOf(4)
|
||||
print("indexOf(4): " + result.toString())
|
||||
// Expected: 1
|
||||
|
||||
result = arr.indexOf(1)
|
||||
print("indexOf(1): " + result.toString())
|
||||
// Expected: 3 (first occurrence from current order)
|
||||
|
||||
result = arr.indexOf(999)
|
||||
print("indexOf(999): " + result.toString())
|
||||
// Expected: -1 (not found)
|
||||
|
||||
print("\n=== Test 4: slice() method ===")
|
||||
sliceResult = arr.slice(1, 4)
|
||||
print("slice(1, 4): " + sliceResult.toString())
|
||||
// Expected: [4, 3, 1] (indices 1, 2, 3)
|
||||
|
||||
sliceResult = arr.slice(0, 2)
|
||||
print("slice(0, 2): " + sliceResult.toString())
|
||||
// Expected: [5, 4] (indices 0, 1)
|
||||
|
||||
sliceResult = arr.slice(2, 10) // End beyond array
|
||||
print("slice(2, 10): " + sliceResult.toString())
|
||||
// Expected: [3, 1, 1] (indices 2 to end)
|
||||
|
||||
print("\n=== Test 5: Mixed types sorting ===")
|
||||
local mixedArr
|
||||
mixedArr = new ArrayBox()
|
||||
mixedArr.push("banana")
|
||||
mixedArr.push(2)
|
||||
mixedArr.push("apple")
|
||||
mixedArr.push(1)
|
||||
mixedArr.push("cherry")
|
||||
print("Mixed array before sort: " + mixedArr.toString())
|
||||
|
||||
mixedArr.sort()
|
||||
print("Mixed array after sort: " + mixedArr.toString())
|
||||
// Expected: numbers first (1, 2), then strings alphabetically
|
||||
|
||||
print("\n=== Test 6: FloatBox integration ===")
|
||||
local floatArr
|
||||
floatArr = new ArrayBox()
|
||||
floatArr.push(new FloatBox(3.14))
|
||||
floatArr.push(1)
|
||||
floatArr.push(new FloatBox(2.71))
|
||||
floatArr.push(4)
|
||||
print("Float array before sort: " + floatArr.toString())
|
||||
|
||||
floatArr.sort()
|
||||
print("Float array after sort: " + floatArr.toString())
|
||||
// Expected: [1, 2.71, 3.14, 4]
|
||||
|
||||
print("\n✅ ArrayBox Phase 2 improvements tests completed!")
|
||||
@ -1,65 +0,0 @@
|
||||
// test_array_methods.nyash - ArrayBox改良テスト
|
||||
// Phase 1: ArrayBox sort(), reverse(), indexOf(), slice() validation
|
||||
|
||||
print("🗂️ Testing ArrayBox improvements...")
|
||||
|
||||
// Create and populate array
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
arr.push(3)
|
||||
arr.push(1)
|
||||
arr.push(2)
|
||||
|
||||
print("Original: " + arr.toString())
|
||||
|
||||
// Test sort() method
|
||||
arr.sort()
|
||||
print("Sorted: " + arr.toString())
|
||||
|
||||
// Test reverse() method
|
||||
arr.reverse()
|
||||
print("Reversed: " + arr.toString())
|
||||
|
||||
// Test indexOf() method
|
||||
local index
|
||||
index = arr.indexOf(2)
|
||||
print("Index of 2: " + index.toString())
|
||||
|
||||
index = arr.indexOf(1)
|
||||
print("Index of 1: " + index.toString())
|
||||
|
||||
index = arr.indexOf(99)
|
||||
print("Index of 99: " + index.toString())
|
||||
|
||||
// Test slice() method
|
||||
local slice
|
||||
slice = arr.slice(0, 2)
|
||||
print("Slice [0,2): " + slice.toString())
|
||||
|
||||
slice = arr.slice(1, 3)
|
||||
print("Slice [1,3): " + slice.toString())
|
||||
|
||||
// Test with string array
|
||||
local strArr
|
||||
strArr = new ArrayBox()
|
||||
strArr.push("zebra")
|
||||
strArr.push("apple")
|
||||
strArr.push("banana")
|
||||
|
||||
print("String array original: " + strArr.toString())
|
||||
|
||||
strArr.sort()
|
||||
print("String array sorted: " + strArr.toString())
|
||||
|
||||
strArr.reverse()
|
||||
print("String array reversed: " + strArr.toString())
|
||||
|
||||
// Test indexOf on strings
|
||||
index = strArr.indexOf("apple")
|
||||
print("Index of 'apple': " + index.toString())
|
||||
|
||||
// Test slice on strings
|
||||
slice = strArr.slice(0, 2)
|
||||
print("String slice [0,2): " + slice.toString())
|
||||
|
||||
print("✅ ArrayBox improvements Phase 1 tests completed!")
|
||||
@ -1,23 +0,0 @@
|
||||
// ArrayBox簡単なテスト
|
||||
print("=== ArrayBox簡単なテスト ===")
|
||||
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
print("Created ArrayBox")
|
||||
|
||||
// 要素を追加
|
||||
arr.push("Hello")
|
||||
arr.push("World")
|
||||
print("Added elements")
|
||||
|
||||
// 長さを確認
|
||||
print("Length: " + arr.length())
|
||||
|
||||
// 配列の内容を表示
|
||||
print("Array: " + arr.toString())
|
||||
|
||||
// 要素を取得
|
||||
print("First element: " + arr.get(0))
|
||||
print("Second element: " + arr.get(1))
|
||||
|
||||
print("\n=== Test complete! ===")
|
||||
@ -1,46 +0,0 @@
|
||||
// Comprehensive test to verify Basic Box constructors work identically to literals
|
||||
// This demonstrates that Problem 1 is fully resolved
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("=== Comprehensive Basic Box Constructor Test ===")
|
||||
|
||||
// Test StringBox equivalence
|
||||
local str_box = new StringBox("test")
|
||||
local str_literal = "test"
|
||||
console.log("StringBox toString: " + str_box.toString())
|
||||
console.log("String literal: " + str_literal)
|
||||
console.log("StringBox == literal: " + (str_box.toString() == str_literal))
|
||||
|
||||
console.log("---")
|
||||
|
||||
// Test IntegerBox equivalence
|
||||
local int_box = new IntegerBox(123)
|
||||
local int_literal = 123
|
||||
console.log("IntegerBox toString: " + int_box.toString())
|
||||
console.log("Integer literal: " + int_literal)
|
||||
console.log("IntegerBox == literal: " + (int_box.toString() == int_literal.toString()))
|
||||
|
||||
console.log("---")
|
||||
|
||||
// Test BoolBox equivalence
|
||||
local bool_box = new BoolBox(true)
|
||||
local bool_literal = true
|
||||
console.log("BoolBox toString: " + bool_box.toString())
|
||||
console.log("Bool literal: " + bool_literal)
|
||||
console.log("BoolBox == literal: " + (bool_box.toString() == bool_literal.toString()))
|
||||
|
||||
console.log("---")
|
||||
|
||||
// Test type conversion capabilities
|
||||
local str_from_int = new StringBox(456)
|
||||
console.log("StringBox from int: " + str_from_int.toString())
|
||||
|
||||
local int_from_str = new IntegerBox("789")
|
||||
console.log("IntegerBox from string: " + int_from_str.toString())
|
||||
|
||||
local bool_from_str_true = new BoolBox("true")
|
||||
local bool_from_str_false = new BoolBox("false")
|
||||
console.log("BoolBox from 'true': " + bool_from_str_true.toString())
|
||||
console.log("BoolBox from 'false': " + bool_from_str_false.toString())
|
||||
|
||||
console.log("=== All Basic Box Constructors Working! ===")
|
||||
@ -1,32 +0,0 @@
|
||||
// Test Basic Box Constructor Issues (Problem 1)
|
||||
// This should demonstrate the core failures described in the issue
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("=== Testing Basic Box Constructors ===")
|
||||
|
||||
// Test StringBox constructor
|
||||
console.log("Testing StringBox constructor...")
|
||||
local str_box = new StringBox("test")
|
||||
console.log("StringBox created: " + str_box.toString())
|
||||
|
||||
// Test IntegerBox constructor
|
||||
console.log("Testing IntegerBox constructor...")
|
||||
local int_box = new IntegerBox(123)
|
||||
console.log("IntegerBox created: " + int_box.toString())
|
||||
|
||||
// Test BoolBox constructor
|
||||
console.log("Testing BoolBox constructor...")
|
||||
local bool_box = new BoolBox(false)
|
||||
console.log("BoolBox created: " + bool_box.toString())
|
||||
|
||||
// Compare with literals (these should work)
|
||||
console.log("=== Comparing with Literals ===")
|
||||
local str_literal = "test"
|
||||
local int_literal = 123
|
||||
local bool_literal = false
|
||||
|
||||
console.log("String literal: " + str_literal)
|
||||
console.log("Integer literal: " + int_literal)
|
||||
console.log("Bool literal: " + bool_literal)
|
||||
|
||||
console.log("Test complete!")
|
||||
@ -1,31 +0,0 @@
|
||||
// 🧪 基本的な新Box テスト
|
||||
|
||||
print("=== Basic New Boxes Test ===")
|
||||
|
||||
// 📦 ArrayBox Test (already working)
|
||||
print("\n✅ ArrayBox:")
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
arr.push("test")
|
||||
print("ArrayBox works: " + arr.length())
|
||||
|
||||
// 🗄️ MapBox Test (already working)
|
||||
print("\n✅ MapBox:")
|
||||
local map
|
||||
map = new MapBox()
|
||||
map.set("key", "value")
|
||||
print("MapBox works: " + map.size())
|
||||
|
||||
// 📊 BufferBox Test
|
||||
print("\n🔹 BufferBox:")
|
||||
local buffer
|
||||
buffer = new BufferBox()
|
||||
print("BufferBox created: " + buffer.toString())
|
||||
|
||||
// 🔍 RegexBox Test
|
||||
print("\n🔹 RegexBox:")
|
||||
local regex
|
||||
regex = new RegexBox("[0-9]+")
|
||||
print("RegexBox created: " + regex.toString())
|
||||
|
||||
print("\n🎉 Basic new Box creation tests completed!")
|
||||
@ -1,35 +0,0 @@
|
||||
// 🧪 新Box作成テスト - メソッド呼び出しなし
|
||||
|
||||
print("=== New Box Creation Test ===")
|
||||
|
||||
// 📊 BufferBox Test
|
||||
print("🔹 Creating BufferBox...")
|
||||
local buffer
|
||||
buffer = new BufferBox()
|
||||
print("✅ BufferBox created successfully!")
|
||||
|
||||
// 🔍 RegexBox Test
|
||||
print("🔹 Creating RegexBox...")
|
||||
local regex
|
||||
regex = new RegexBox("[0-9]+")
|
||||
print("✅ RegexBox created successfully!")
|
||||
|
||||
// 📋 JSONBox Test
|
||||
print("🔹 Creating JSONBox...")
|
||||
local json
|
||||
json = new JSONBox("{\"name\": \"test\"}")
|
||||
print("✅ JSONBox created successfully!")
|
||||
|
||||
// 🌊 StreamBox Test
|
||||
print("🔹 Creating StreamBox...")
|
||||
local stream
|
||||
stream = new StreamBox()
|
||||
print("✅ StreamBox created successfully!")
|
||||
|
||||
// 🌐 HTTPClientBox Test
|
||||
print("🔹 Creating HTTPClientBox...")
|
||||
local http
|
||||
http = new HTTPClientBox()
|
||||
print("✅ HTTPClientBox created successfully!")
|
||||
|
||||
print("\n🎉 All Arc<Mutex> Boxes created successfully!")
|
||||
@ -1,56 +0,0 @@
|
||||
// Test program to verify NyashBox implementations work
|
||||
static box TestBoxes {
|
||||
init { console, result }
|
||||
|
||||
main() {
|
||||
me.console = new ConsoleBox()
|
||||
me.console.log("🎯 Testing NyashBox implementations...")
|
||||
|
||||
// Test completed boxes
|
||||
me.testArrayBox()
|
||||
me.testBufferBox()
|
||||
me.testJSONBox()
|
||||
me.testResultBox()
|
||||
me.testFutureBox()
|
||||
me.testStreamBox()
|
||||
|
||||
me.result = "All NyashBox tests completed!"
|
||||
return me.result
|
||||
}
|
||||
|
||||
testArrayBox() {
|
||||
me.console.log("📦 Testing ArrayBox...")
|
||||
// Basic functionality would be tested here when ArrayBox methods are integrated
|
||||
me.console.log("ArrayBox test passed!")
|
||||
}
|
||||
|
||||
testBufferBox() {
|
||||
me.console.log("📊 Testing BufferBox...")
|
||||
// Basic functionality would be tested here when BufferBox methods are integrated
|
||||
me.console.log("BufferBox test passed!")
|
||||
}
|
||||
|
||||
testJSONBox() {
|
||||
me.console.log("📋 Testing JSONBox...")
|
||||
// Basic functionality would be tested here when JSONBox methods are integrated
|
||||
me.console.log("JSONBox test passed!")
|
||||
}
|
||||
|
||||
testResultBox() {
|
||||
me.console.log("⚠️ Testing ResultBox...")
|
||||
// Basic functionality would be tested here when ResultBox methods are integrated
|
||||
me.console.log("ResultBox test passed!")
|
||||
}
|
||||
|
||||
testFutureBox() {
|
||||
me.console.log("🔄 Testing FutureBox...")
|
||||
// Basic functionality would be tested here when FutureBox methods are integrated
|
||||
me.console.log("FutureBox test passed!")
|
||||
}
|
||||
|
||||
testStreamBox() {
|
||||
me.console.log("🌊 Testing StreamBox...")
|
||||
// Basic functionality would be tested here when StreamBox methods are integrated
|
||||
me.console.log("StreamBox test passed!")
|
||||
}
|
||||
}
|
||||
@ -1,27 +0,0 @@
|
||||
// 🧪 BufferBoxのテスト
|
||||
|
||||
print("=== BufferBox Test ===")
|
||||
local buffer, data, result
|
||||
|
||||
// BufferBox作成
|
||||
buffer = new BufferBox()
|
||||
|
||||
// データ配列作成
|
||||
data = new ArrayBox()
|
||||
data.push(72) // 'H'
|
||||
data.push(101) // 'e'
|
||||
data.push(108) // 'l'
|
||||
data.push(108) // 'l'
|
||||
data.push(111) // 'o'
|
||||
|
||||
// データ書き込み
|
||||
result = buffer.write(data)
|
||||
print("Write result: " + result)
|
||||
print("Buffer length: " + buffer.length())
|
||||
|
||||
// データ読み取り
|
||||
local readData
|
||||
readData = buffer.readAll()
|
||||
print("Read data: " + readData)
|
||||
|
||||
print("BufferBox test completed!")
|
||||
@ -1,77 +0,0 @@
|
||||
// test_comparison_operators.nyash - Comparison operators test
|
||||
// Phase 4: Comparison operators implementation validation
|
||||
|
||||
print("⚖️ Testing comparison operators implementation...")
|
||||
|
||||
// Basic variables for testing
|
||||
local f1, f2, i1, i2, s1, s2, result
|
||||
|
||||
// Test FloatBox comparisons
|
||||
f1 = new FloatBox(3.14)
|
||||
f2 = new FloatBox(2.86)
|
||||
|
||||
print("=== FloatBox Comparisons ===")
|
||||
result = f1 > f2
|
||||
print("3.14 > 2.86: " + result.toString())
|
||||
|
||||
result = f1 < f2
|
||||
print("3.14 < 2.86: " + result.toString())
|
||||
|
||||
result = f1 >= f2
|
||||
print("3.14 >= 2.86: " + result.toString())
|
||||
|
||||
result = f1 <= f2
|
||||
print("3.14 <= 2.86: " + result.toString())
|
||||
|
||||
result = f1 == f2
|
||||
print("3.14 == 2.86: " + result.toString())
|
||||
|
||||
result = f1 != f2
|
||||
print("3.14 != 2.86: " + result.toString())
|
||||
|
||||
// Test IntegerBox comparisons
|
||||
i1 = 10
|
||||
i2 = 5
|
||||
|
||||
print("=== IntegerBox Comparisons ===")
|
||||
result = i1 > i2
|
||||
print("10 > 5: " + result.toString())
|
||||
|
||||
result = i1 < i2
|
||||
print("10 < 5: " + result.toString())
|
||||
|
||||
result = i1 >= i2
|
||||
print("10 >= 5: " + result.toString())
|
||||
|
||||
result = i1 <= i2
|
||||
print("10 <= 5: " + result.toString())
|
||||
|
||||
result = i1 == i2
|
||||
print("10 == 5: " + result.toString())
|
||||
|
||||
result = i1 != i2
|
||||
print("10 != 5: " + result.toString())
|
||||
|
||||
// Test mixed type comparisons (FloatBox vs IntegerBox)
|
||||
print("=== Mixed Type Comparisons ===")
|
||||
result = f1 > i2
|
||||
print("3.14 > 5: " + result.toString())
|
||||
|
||||
result = f1 < i1
|
||||
print("3.14 < 10: " + result.toString())
|
||||
|
||||
result = i1 >= f1
|
||||
print("10 >= 3.14: " + result.toString())
|
||||
|
||||
result = i2 <= f2
|
||||
print("5 <= 2.86: " + result.toString())
|
||||
|
||||
// Test logical operators
|
||||
print("=== Logical Operators ===")
|
||||
result = (f1 > f2) and (i1 > i2)
|
||||
print("(3.14 > 2.86) and (10 > 5): " + result.toString())
|
||||
|
||||
result = (f1 < f2) or (i1 > i2)
|
||||
print("(3.14 < 2.86) or (10 > 5): " + result.toString())
|
||||
|
||||
print("✅ Comparison operators Phase 4 tests completed!")
|
||||
@ -1,68 +0,0 @@
|
||||
// 🎉 COMPREHENSIVE TEST - All Issues Resolved!
|
||||
// Tests all the originally reported problems have been fixed
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("🎉 === COMPREHENSIVE TEST: All Issues Resolved ===")
|
||||
|
||||
console.log("--- Phase 1: Basic Box Constructors (Problem 1) ---")
|
||||
// ✅ FIXED: These were originally failing with "Undefined class" errors
|
||||
local str_box = new StringBox("test")
|
||||
local int_box = new IntegerBox(123)
|
||||
local bool_box = new BoolBox(true)
|
||||
console.log("✅ StringBox: " + str_box.toString())
|
||||
console.log("✅ IntegerBox: " + int_box.toString())
|
||||
console.log("✅ BoolBox: " + bool_box.toString())
|
||||
|
||||
console.log("--- Problem 2: IntentBox Field Access (Already Working) ---")
|
||||
// ✅ CONFIRMED: These were actually working fine
|
||||
local intent = new IntentBox("test", "Hello World")
|
||||
console.log("✅ IntentBox name: " + intent.getName())
|
||||
console.log("✅ IntentBox payload: " + intent.getPayload())
|
||||
|
||||
console.log("--- Problem 4: FloatBox (Already Working) ---")
|
||||
// ✅ CONFIRMED: This was also working fine
|
||||
local float = new FloatBox(3.14)
|
||||
console.log("✅ FloatBox: " + float.toString())
|
||||
|
||||
console.log("--- Phase 2: Multi-Delegation (NEW FEATURE) ---")
|
||||
// 🚀 NEW: Revolutionary multi-delegation syntax implementation
|
||||
box SuperBox from StringBox, IntegerBox, BoolBox {
|
||||
init { text, number, flag }
|
||||
|
||||
pack(t, n, f) {
|
||||
me.text = t
|
||||
me.number = n
|
||||
me.flag = f
|
||||
}
|
||||
|
||||
getAllData() {
|
||||
return "SuperBox[" + me.text + ", " + me.number + ", " + me.flag + "]"
|
||||
}
|
||||
}
|
||||
|
||||
local super = new SuperBox("Multi", 42, true)
|
||||
console.log("🚀 Multi-delegation: " + super.getAllData())
|
||||
|
||||
console.log("--- Backward Compatibility Tests ---")
|
||||
// ✅ CONFIRMED: All old syntax still works
|
||||
box OldStyle from StringBox {
|
||||
init { data }
|
||||
pack(d) { me.data = d }
|
||||
getData() { return "Old: " + me.data }
|
||||
}
|
||||
|
||||
box NoParents {
|
||||
init { value }
|
||||
pack(v) { me.value = v }
|
||||
getValue() { return "Standalone: " + me.value }
|
||||
}
|
||||
|
||||
local old = new OldStyle("SingleParent")
|
||||
local standalone = new NoParents("Independent")
|
||||
console.log("✅ Single parent: " + old.getData())
|
||||
console.log("✅ No parents: " + standalone.getValue())
|
||||
|
||||
console.log("🎊 === ALL ISSUES RESOLVED & NEW FEATURES WORKING! ===")
|
||||
console.log("🎯 Phase 1: Critical Box registration COMPLETE")
|
||||
console.log("🚀 Phase 2: Multi-delegation syntax COMPLETE")
|
||||
console.log("✅ Ready for P2P development with advanced delegation patterns!")
|
||||
@ -1,115 +0,0 @@
|
||||
// test_cross_type_operators.nyash - 演算子システム強化テスト
|
||||
// Phase 1: Cross-type operations, string concatenation, comparisons validation
|
||||
|
||||
print("🔢 Testing cross-type operators implementation...")
|
||||
|
||||
// Test 1: IntegerBox + FloatBox
|
||||
print("=== Type Conversion Tests ===")
|
||||
local i, f, result
|
||||
i = 10
|
||||
f = new FloatBox(3.14)
|
||||
result = i + f
|
||||
print("10 + 3.14 = " + result.toString())
|
||||
|
||||
result = f + i
|
||||
print("3.14 + 10 = " + result.toString())
|
||||
|
||||
// Test multiplication
|
||||
result = i * f
|
||||
print("10 * 3.14 = " + result.toString())
|
||||
|
||||
result = f * i
|
||||
print("3.14 * 10 = " + result.toString())
|
||||
|
||||
// Test division
|
||||
result = i / f
|
||||
print("10 / 3.14 = " + result.toString())
|
||||
|
||||
result = f / i
|
||||
print("3.14 / 10 = " + result.toString())
|
||||
|
||||
// Test subtraction
|
||||
result = i - f
|
||||
print("10 - 3.14 = " + result.toString())
|
||||
|
||||
result = f - i
|
||||
print("3.14 - 10 = " + result.toString())
|
||||
|
||||
// Test 2: String concatenation with numbers
|
||||
print("\n=== String Concatenation Tests ===")
|
||||
local text, num, boolVal
|
||||
text = "Value: "
|
||||
num = 42
|
||||
boolVal = true
|
||||
|
||||
result = text + num
|
||||
print("\"Value: \" + 42 = " + result)
|
||||
|
||||
result = text + f
|
||||
print("\"Value: \" + 3.14 = " + result)
|
||||
|
||||
result = text + boolVal
|
||||
print("\"Value: \" + true = " + result)
|
||||
|
||||
// Reverse concatenation
|
||||
result = num + " items"
|
||||
print("42 + \" items\" = " + result)
|
||||
|
||||
// Test 3: Cross-type comparisons
|
||||
print("\n=== Cross-Type Comparison Tests ===")
|
||||
local comparison
|
||||
|
||||
comparison = f > i
|
||||
print("3.14 > 10: " + comparison.toString())
|
||||
|
||||
comparison = i > f
|
||||
print("10 > 3.14: " + comparison.toString())
|
||||
|
||||
comparison = f < i
|
||||
print("3.14 < 10: " + comparison.toString())
|
||||
|
||||
comparison = i < f
|
||||
print("10 < 3.14: " + comparison.toString())
|
||||
|
||||
comparison = f >= i
|
||||
print("3.14 >= 10: " + comparison.toString())
|
||||
|
||||
comparison = i <= f
|
||||
print("10 <= 3.14: " + comparison.toString())
|
||||
|
||||
comparison = f == i
|
||||
print("3.14 == 10: " + comparison.toString())
|
||||
|
||||
comparison = f != i
|
||||
print("3.14 != 10: " + comparison.toString())
|
||||
|
||||
// Test 4: Complex expressions
|
||||
print("\n=== Complex Expression Tests ===")
|
||||
local complex
|
||||
|
||||
complex = (i + f) > 12
|
||||
print("(10 + 3.14) > 12: " + complex.toString())
|
||||
|
||||
complex = (f * 2) < (i - 3)
|
||||
print("(3.14 * 2) < (10 - 3): " + complex.toString())
|
||||
|
||||
complex = (i > 5) and (f > 3)
|
||||
print("(10 > 5) and (3.14 > 3): " + complex.toString())
|
||||
|
||||
complex = (i < 5) or (f > 3)
|
||||
print("(10 < 5) or (3.14 > 3): " + complex.toString())
|
||||
|
||||
// Test 5: Number to string auto-conversion in concatenation
|
||||
print("\n=== Auto-Conversion Tests ===")
|
||||
local auto1, auto2, auto3
|
||||
|
||||
auto1 = "Result: " + (i + f)
|
||||
print("\"Result: \" + (10 + 3.14) = " + auto1)
|
||||
|
||||
auto2 = "Boolean: " + (i > f)
|
||||
print("\"Boolean: \" + (10 > 3.14) = " + auto2)
|
||||
|
||||
auto3 = "Math: " + (f * f)
|
||||
print("\"Math: \" + (3.14 * 3.14) = " + auto3)
|
||||
|
||||
print("\n✅ Cross-type operators Phase 1 tests completed!")
|
||||
@ -1,43 +0,0 @@
|
||||
// test_datetime_box.nyash - DateTimeBox functionality test
|
||||
// Phase 3: DateTimeBox implementation validation
|
||||
|
||||
print("📅 Testing DateTimeBox implementation...")
|
||||
|
||||
// Basic DateTimeBox creation
|
||||
local now, timestamp_dt, parsed_dt, result
|
||||
|
||||
// Test 1: Current time creation
|
||||
now = new DateTimeBox()
|
||||
print("Current time: " + now.toString())
|
||||
|
||||
// Test 2: Timestamp creation
|
||||
timestamp_dt = new DateTimeBox(1640995200) // 2022-01-01 00:00:00 UTC
|
||||
print("From timestamp: " + timestamp_dt.toString())
|
||||
|
||||
// Test 3: Date component extraction
|
||||
result = now.year()
|
||||
print("Current year: " + result.toString())
|
||||
|
||||
result = now.month()
|
||||
print("Current month: " + result.toString())
|
||||
|
||||
result = now.day()
|
||||
print("Current day: " + result.toString())
|
||||
|
||||
result = now.hour()
|
||||
print("Current hour: " + result.toString())
|
||||
|
||||
result = now.minute()
|
||||
print("Current minute: " + result.toString())
|
||||
|
||||
result = now.second()
|
||||
print("Current second: " + result.toString())
|
||||
|
||||
// Test 4: Date arithmetic
|
||||
result = now.addDays(7)
|
||||
print("7 days from now: " + result.toString())
|
||||
|
||||
result = now.addHours(24)
|
||||
print("24 hours from now: " + result.toString())
|
||||
|
||||
print("✅ DateTimeBox Phase 3 tests completed!")
|
||||
@ -1,4 +0,0 @@
|
||||
// test_datetime_tostring.nyash - DateTimeBox toString() test as mentioned in issue
|
||||
local dt
|
||||
dt = new DateTimeBox()
|
||||
print(dt.toString())
|
||||
@ -1,83 +0,0 @@
|
||||
// Final comprehensive weak reference auto-nil test
|
||||
|
||||
// Global flag to simulate object dropping
|
||||
box GlobalState {
|
||||
init { parentDropped }
|
||||
|
||||
pack() {
|
||||
me.parentDropped = false
|
||||
}
|
||||
|
||||
setParentDropped(dropped) {
|
||||
me.parentDropped = dropped
|
||||
}
|
||||
|
||||
isParentDropped() {
|
||||
return me.parentDropped
|
||||
}
|
||||
}
|
||||
|
||||
box Parent {
|
||||
init { name, child }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
me.child = new Child()
|
||||
me.child.setParent(me) // This creates a weak reference
|
||||
}
|
||||
|
||||
getChild() {
|
||||
return me.child
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
getParentStatus() {
|
||||
// Check if parent is still alive using the global state
|
||||
local state = new GlobalState()
|
||||
local dropped = state.isParentDropped()
|
||||
|
||||
if dropped {
|
||||
return "Parent is null (dropped)"
|
||||
} else {
|
||||
return "Parent exists"
|
||||
}
|
||||
}
|
||||
|
||||
checkWeakParent() {
|
||||
return me.parent
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== Complete Weak Reference Auto-Nil Test ===")
|
||||
|
||||
local state = new GlobalState()
|
||||
|
||||
local parent = new Parent("TestParent")
|
||||
local child = parent.getChild()
|
||||
|
||||
print("Step 1: Initial setup")
|
||||
print("Initial status: " + child.getParentStatus())
|
||||
|
||||
print("Step 2: Simulating parent drop")
|
||||
state.setParentDropped(true) // Mark parent as dropped
|
||||
parent = 0 // This triggers the weak reference invalidation
|
||||
|
||||
print("Step 3: Checking weak reference after drop")
|
||||
print("Final status: " + child.getParentStatus())
|
||||
|
||||
return "weak reference auto-nil demonstration completed"
|
||||
}
|
||||
}
|
||||
@ -1,119 +0,0 @@
|
||||
// 🔥 Comprehensive fini System Test - ChatGPT5 Design Validation
|
||||
|
||||
// Test Case 1: Basic finalization and usage prohibition
|
||||
box SimpleResource {
|
||||
init { name, value }
|
||||
|
||||
pack(resourceName) {
|
||||
me.name = resourceName
|
||||
me.value = 42
|
||||
}
|
||||
|
||||
getValue() {
|
||||
return me.value
|
||||
}
|
||||
|
||||
fini() {
|
||||
print("🔥 SimpleResource.fini(): Cleaning up " + me.name.toString())
|
||||
}
|
||||
}
|
||||
|
||||
// Test Case 2: Circular reference with weak fields
|
||||
box Parent {
|
||||
init { name, weak child }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
}
|
||||
|
||||
setChild(c) {
|
||||
me.child = c
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { id, parent }
|
||||
|
||||
pack(childId, p) {
|
||||
me.id = childId
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
// Test Case 3: weak-fini prohibition
|
||||
fini() {
|
||||
print("🔥 Child.fini(): Cleaning up child " + me.id.toString())
|
||||
// me.parent.fini() // This should be caught and prevented
|
||||
}
|
||||
}
|
||||
|
||||
// Test Case 4: Deterministic cascade finalization
|
||||
box Pipeline {
|
||||
init { r1, r2, r3, weak monitor }
|
||||
|
||||
pack(name) {
|
||||
me.r1 = new SimpleResource(name + "_r1")
|
||||
me.r2 = new SimpleResource(name + "_r2")
|
||||
me.r3 = new SimpleResource(name + "_r3")
|
||||
}
|
||||
|
||||
setMonitor(m) {
|
||||
me.monitor = m
|
||||
}
|
||||
|
||||
// Custom fini with specific order control
|
||||
fini() {
|
||||
print("🔥 Pipeline.fini(): Custom cleanup order")
|
||||
// Reverse dependency order: r3 → r2 (r1 will be auto-cascade)
|
||||
me.r3.fini()
|
||||
me.r2.fini()
|
||||
// r1 should be automatically finalized by cascade
|
||||
// monitor is weak, so it's not finalized
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== 🔥 Comprehensive fini System Test ===")
|
||||
|
||||
// Test 1: Basic finalization
|
||||
print("\n📋 Test 1: Basic finalization and usage prohibition")
|
||||
local resource = new SimpleResource("TestResource")
|
||||
print("Resource value before fini: " + resource.getValue().toString())
|
||||
|
||||
resource.fini()
|
||||
print("Resource finalized")
|
||||
|
||||
// This should throw an error - usage after finalization
|
||||
// print("Trying to access finalized resource...")
|
||||
// resource.getValue() // Should fail with "Instance was finalized"
|
||||
|
||||
// Test 2: Circular reference handling
|
||||
print("\n📋 Test 2: Circular reference with weak fields")
|
||||
local parent = new Parent("TestParent")
|
||||
local child = new Child("child1", parent)
|
||||
parent.setChild(child)
|
||||
|
||||
print("Parent: " + parent.getName().toString())
|
||||
print("Before parent finalization")
|
||||
|
||||
parent.fini()
|
||||
print("Parent finalized - child's weak reference should be safe")
|
||||
|
||||
// Test 3: Deterministic cascade finalization
|
||||
print("\n📋 Test 3: Deterministic cascade finalization")
|
||||
local pipeline = new Pipeline("TestPipeline")
|
||||
local monitor = new SimpleResource("Monitor")
|
||||
pipeline.setMonitor(monitor)
|
||||
|
||||
print("Pipeline created with resources and monitor")
|
||||
pipeline.fini()
|
||||
print("Pipeline finalized with custom order + auto-cascade")
|
||||
|
||||
print("\n✅ fini System Test Completed!")
|
||||
return "All tests passed"
|
||||
}
|
||||
}
|
||||
@ -1,51 +0,0 @@
|
||||
// 🔥 fini System Violation Tests - Testing guards and prohibitions
|
||||
|
||||
box TestResource {
|
||||
init { name }
|
||||
|
||||
pack(resourceName) {
|
||||
me.name = resourceName
|
||||
}
|
||||
|
||||
getData() {
|
||||
return "Resource: " + me.name.toString()
|
||||
}
|
||||
|
||||
fini() {
|
||||
print("🔥 TestResource.fini(): Finalizing " + me.name.toString())
|
||||
}
|
||||
}
|
||||
|
||||
box BadExample {
|
||||
init { weak weakRef, strongRef }
|
||||
|
||||
pack(name) {
|
||||
me.strongRef = new TestResource(name + "_strong")
|
||||
me.weakRef = new TestResource(name + "_weak") // Will be set as weak
|
||||
}
|
||||
|
||||
// This should trigger weak-fini prohibition
|
||||
badFini() {
|
||||
print("🔥 BadExample.badFini(): Attempting illegal operations")
|
||||
me.weakRef.fini() // Should fail with "Cannot finalize weak field"
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== 🔥 fini System Violation Tests ===")
|
||||
|
||||
// Test 1: Usage after finalization prohibition
|
||||
print("\n📋 Test 1: Usage after finalization (should fail)")
|
||||
local resource = new TestResource("TestViolation")
|
||||
print("Before fini: " + resource.getData())
|
||||
|
||||
resource.fini()
|
||||
print("Resource finalized")
|
||||
|
||||
print("Attempting to access finalized resource...")
|
||||
resource.getData() // Should fail with "Instance was finalized"
|
||||
|
||||
return "Test should have failed before reaching here"
|
||||
}
|
||||
}
|
||||
@ -1,49 +0,0 @@
|
||||
// test_float_box.nyash - FloatBox functionality test
|
||||
// Phase 1: Basic FloatBox implementation validation
|
||||
|
||||
print("🧮 Testing FloatBox implementation...")
|
||||
|
||||
// Basic FloatBox creation
|
||||
local f1, f2, result
|
||||
f1 = new FloatBox(3.14)
|
||||
f2 = new FloatBox(2.86)
|
||||
|
||||
print("Created FloatBox f1: " + f1.toString())
|
||||
print("Created FloatBox f2: " + f2.toString())
|
||||
|
||||
// Addition test
|
||||
result = f1 + f2
|
||||
print("3.14 + 2.86 = " + result.toString())
|
||||
|
||||
// Multiplication test
|
||||
result = f1 * f2
|
||||
print("3.14 * 2.86 = " + result.toString())
|
||||
|
||||
// Division test
|
||||
result = f1 / f2
|
||||
print("3.14 / 2.86 = " + result.toString())
|
||||
|
||||
// Subtraction test
|
||||
result = f1 - f2
|
||||
print("3.14 - 2.86 = " + result.toString())
|
||||
|
||||
// Mixed operations with IntegerBox
|
||||
local intVal
|
||||
intVal = 5
|
||||
result = f1 + intVal
|
||||
print("3.14 + 5 = " + result.toString())
|
||||
|
||||
result = f1 * intVal
|
||||
print("3.14 * 5 = " + result.toString())
|
||||
|
||||
// FloatBox methods
|
||||
result = f1.abs()
|
||||
print("abs(3.14) = " + result.toString())
|
||||
|
||||
result = f1.floor()
|
||||
print("floor(3.14) = " + result.toString())
|
||||
|
||||
result = f1.ceil()
|
||||
print("ceil(3.14) = " + result.toString())
|
||||
|
||||
print("✅ FloatBox Phase 1 tests completed!")
|
||||
@ -1,22 +0,0 @@
|
||||
// Test FloatBox Issues (Problem 4)
|
||||
// This should demonstrate the FloatBox value access issues
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("=== Testing FloatBox Issues ===")
|
||||
|
||||
// Test FloatBox creation (this should work)
|
||||
console.log("Creating FloatBox...")
|
||||
local float = new FloatBox(3.14)
|
||||
console.log("FloatBox created successfully")
|
||||
|
||||
// Test toString method (this should work)
|
||||
console.log("Testing toString...")
|
||||
local float_str = float.toString()
|
||||
console.log("FloatBox toString: " + float_str)
|
||||
|
||||
// Test value field access (this should fail)
|
||||
console.log("Testing value field access...")
|
||||
// local value = float.value
|
||||
// console.log("FloatBox value: " + value)
|
||||
|
||||
console.log("FloatBox test complete!")
|
||||
@ -1,4 +0,0 @@
|
||||
// test_float_tostring.nyash - FloatBox toString() test as mentioned in issue
|
||||
local f1
|
||||
f1 = new FloatBox(3.14)
|
||||
print(f1.toString())
|
||||
@ -1,106 +0,0 @@
|
||||
// 🔥 FromCall実装テスト - Override + From統一構文によるデリゲーション革命
|
||||
|
||||
// 親クラス定義
|
||||
box Animal {
|
||||
init { name, sound }
|
||||
|
||||
constructor() {
|
||||
me.name = "Unknown Animal"
|
||||
me.sound = "Silent"
|
||||
}
|
||||
|
||||
constructor(animalName) {
|
||||
me.name = animalName
|
||||
me.sound = "Unknown Sound"
|
||||
}
|
||||
|
||||
makeSound() {
|
||||
local console
|
||||
console = new ConsoleBox()
|
||||
console.log(me.name + " makes " + me.sound)
|
||||
return me.sound
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
// 子クラス定義(デリゲーション関係)
|
||||
box Dog : Animal {
|
||||
init { breed }
|
||||
|
||||
constructor() {
|
||||
// 親コンストラクタを呼び出し
|
||||
from Animal.constructor()
|
||||
me.sound = "Woof!"
|
||||
me.breed = "Mixed"
|
||||
}
|
||||
|
||||
constructor(dogName, dogBreed) {
|
||||
// 引数付き親コンストラクタを呼び出し
|
||||
from Animal.constructor(dogName)
|
||||
me.sound = "Woof!"
|
||||
me.breed = dogBreed
|
||||
}
|
||||
|
||||
// override: 親メソッドをオーバーライド
|
||||
makeSound() {
|
||||
// 親メソッドを呼び出し
|
||||
local parentSound
|
||||
parentSound = from Animal.makeSound()
|
||||
|
||||
// 追加の処理
|
||||
local console
|
||||
console = new ConsoleBox()
|
||||
console.log("This is a " + me.breed + " breed!")
|
||||
return parentSound
|
||||
}
|
||||
|
||||
getBreed() {
|
||||
return me.breed
|
||||
}
|
||||
|
||||
// 親のgetNameを呼び出すテスト
|
||||
getFullInfo() {
|
||||
local parentName
|
||||
parentName = from Animal.getName()
|
||||
return parentName + " (" + me.breed + ")"
|
||||
}
|
||||
}
|
||||
|
||||
// 静的メインクラス
|
||||
static box Main {
|
||||
init { console }
|
||||
|
||||
main() {
|
||||
me.console = new ConsoleBox()
|
||||
me.console.log("🔥 FromCall Implementation Test Starting...")
|
||||
|
||||
// テスト1: デフォルトコンストラクタ
|
||||
local dog1
|
||||
dog1 = new Dog()
|
||||
me.console.log("Test 1 - Default Constructor:")
|
||||
dog1.makeSound()
|
||||
me.console.log("Name: " + dog1.getName())
|
||||
me.console.log("Breed: " + dog1.getBreed())
|
||||
me.console.log("")
|
||||
|
||||
// テスト2: 引数付きコンストラクタ
|
||||
local dog2
|
||||
dog2 = new Dog("Buddy", "Golden Retriever")
|
||||
me.console.log("Test 2 - Parameterized Constructor:")
|
||||
dog2.makeSound()
|
||||
me.console.log("Full Info: " + dog2.getFullInfo())
|
||||
me.console.log("")
|
||||
|
||||
// テスト3: 親メソッド直接呼び出し
|
||||
me.console.log("Test 3 - Direct parent method call:")
|
||||
local directAnimal
|
||||
directAnimal = new Animal("Cat")
|
||||
directAnimal.makeSound()
|
||||
|
||||
me.console.log("🎉 FromCall Implementation Test Completed!")
|
||||
return "FromCall Revolution Success!"
|
||||
}
|
||||
}
|
||||
@ -1,23 +0,0 @@
|
||||
// Test IntentBox Field Access Issues (Problem 2)
|
||||
// This should demonstrate the field access failures described
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("=== Testing IntentBox Field Access ===")
|
||||
|
||||
// Test IntentBox creation (this should work)
|
||||
console.log("Creating IntentBox...")
|
||||
local intent = new IntentBox("test", "Hello")
|
||||
console.log("IntentBox created successfully")
|
||||
|
||||
// Test field access methods (these should be the issue)
|
||||
console.log("Testing field access...")
|
||||
|
||||
// Try getName method
|
||||
local name = intent.getName()
|
||||
console.log("Intent name: " + name)
|
||||
|
||||
// Try getPayload method
|
||||
local payload = intent.getPayload()
|
||||
console.log("Intent payload: " + payload)
|
||||
|
||||
console.log("Field access test complete!")
|
||||
@ -1,6 +0,0 @@
|
||||
// Test only the IntentBox functionality to verify the basic structure works
|
||||
print("Testing IntentBox basic functionality...")
|
||||
|
||||
local msg
|
||||
msg = new IntentBox("test", "data")
|
||||
print("IntentBox created: " + msg.type())
|
||||
@ -1,32 +0,0 @@
|
||||
// 🚨 無効なoverride検証テスト - エラーが発生すべき
|
||||
|
||||
// 親Box
|
||||
box Animal {
|
||||
init { name }
|
||||
|
||||
pack(animalName) {
|
||||
me.name = animalName
|
||||
}
|
||||
|
||||
speak() {
|
||||
return me.name + " makes a sound"
|
||||
}
|
||||
}
|
||||
|
||||
// 子Box - 存在しないメソッドをoverride(エラーになるはず)
|
||||
box BadDog from Animal {
|
||||
init { breed }
|
||||
|
||||
pack(dogName, dogBreed) {
|
||||
from Animal.pack(dogName)
|
||||
me.breed = dogBreed
|
||||
}
|
||||
|
||||
// 🚨 これはエラーになるはず - nonExistentMethodは危険パターンに含まれている
|
||||
override nonExistentMethod() {
|
||||
return "This should fail"
|
||||
}
|
||||
}
|
||||
|
||||
// このファイルはパースエラーで実行されないはず
|
||||
print("このメッセージが表示されたらテスト失敗")
|
||||
@ -1,21 +0,0 @@
|
||||
// Test MIR control flow and exception handling - Phase 5
|
||||
|
||||
// Test loop functionality
|
||||
local counter
|
||||
counter = 0
|
||||
|
||||
loop(counter < 3) {
|
||||
print(counter)
|
||||
counter = counter + 1
|
||||
}
|
||||
|
||||
// Test try/catch functionality
|
||||
try {
|
||||
print("In try block")
|
||||
throw "Test exception"
|
||||
print("This should not execute")
|
||||
} catch (exception) {
|
||||
print("Caught exception")
|
||||
}
|
||||
|
||||
print("Program completed")
|
||||
@ -1,6 +0,0 @@
|
||||
/*!
|
||||
* Simple test for basic MIR functionality
|
||||
*/
|
||||
|
||||
// A simple Nyash program for testing MIR compilation
|
||||
print(42 + 10)
|
||||
@ -1,28 +0,0 @@
|
||||
// Test Multi-Delegation Syntax (Phase 2 Implementation)
|
||||
// This should test the new `box Child from ParentA, ParentB` syntax
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("=== Testing Multi-Delegation Syntax ===")
|
||||
|
||||
// Test 1: Simple multi-delegation syntax parsing
|
||||
console.log("Testing multi-delegation syntax...")
|
||||
box MultiChild from StringBox, IntegerBox {
|
||||
init { textValue, numValue }
|
||||
|
||||
pack(text, num) {
|
||||
me.textValue = text
|
||||
me.numValue = num
|
||||
}
|
||||
|
||||
getCombined() {
|
||||
return me.textValue + ": " + me.numValue
|
||||
}
|
||||
}
|
||||
|
||||
console.log("Multi-delegation box declared successfully!")
|
||||
|
||||
// Test if the parser accepted the syntax
|
||||
local multi = new MultiChild("Count", 123)
|
||||
console.log("Multi delegation instance: " + multi.getCombined())
|
||||
|
||||
console.log("=== Multi-Delegation Test Complete ===")
|
||||
@ -1,60 +0,0 @@
|
||||
// Advanced Multi-Delegation Test Cases
|
||||
// Testing complex scenarios and edge cases
|
||||
|
||||
local console = new ConsoleBox()
|
||||
console.log("=== Advanced Multi-Delegation Tests ===")
|
||||
|
||||
// Test 1: Three-way delegation
|
||||
console.log("Testing three-way delegation...")
|
||||
box TripleChild from StringBox, IntegerBox, BoolBox {
|
||||
init { strVal, intVal, boolVal }
|
||||
|
||||
pack(s, i, b) {
|
||||
me.strVal = s
|
||||
me.intVal = i
|
||||
me.boolVal = b
|
||||
}
|
||||
|
||||
getAll() {
|
||||
return me.strVal + " | " + me.intVal + " | " + me.boolVal
|
||||
}
|
||||
}
|
||||
|
||||
local triple = new TripleChild("Hello", 42, true)
|
||||
console.log("Triple delegation: " + triple.getAll())
|
||||
|
||||
// Test 2: No delegation (should still work)
|
||||
console.log("Testing no delegation...")
|
||||
box StandaloneBox {
|
||||
init { data }
|
||||
|
||||
pack(value) {
|
||||
me.data = value
|
||||
}
|
||||
|
||||
getData() {
|
||||
return "Standalone: " + me.data
|
||||
}
|
||||
}
|
||||
|
||||
local standalone = new StandaloneBox("Independent")
|
||||
console.log(standalone.getData())
|
||||
|
||||
// Test 3: Single delegation (backward compatibility)
|
||||
console.log("Testing single delegation backward compatibility...")
|
||||
box SingleBox from StringBox {
|
||||
init { value }
|
||||
|
||||
pack(val) {
|
||||
me.value = val
|
||||
}
|
||||
|
||||
getValue() {
|
||||
return "Single: " + me.value
|
||||
}
|
||||
}
|
||||
|
||||
local single = new SingleBox("OnlyOne")
|
||||
console.log(single.getValue())
|
||||
|
||||
console.log("=== All Multi-Delegation Tests Passed! ===")
|
||||
@ -1,113 +0,0 @@
|
||||
// 🧪 新しいBox実装のテスト
|
||||
|
||||
// 1. ArrayBoxのテスト
|
||||
print("=== ArrayBox Test ===")
|
||||
local arr
|
||||
arr = new ArrayBox()
|
||||
|
||||
// push/pop
|
||||
arr.push("Hello")
|
||||
arr.push("World")
|
||||
arr.push(42)
|
||||
print("Length after push: " + arr.length())
|
||||
|
||||
local popped
|
||||
popped = arr.pop()
|
||||
print("Popped: " + popped)
|
||||
print("Length after pop: " + arr.length())
|
||||
|
||||
// get/set
|
||||
print("arr[0]: " + arr.get(0))
|
||||
arr.set(1, "Nyash")
|
||||
print("arr[1] after set: " + arr.get(1))
|
||||
|
||||
// join
|
||||
print("Joined: " + arr.join(", "))
|
||||
|
||||
// 2. BufferBoxのテスト
|
||||
print("\n=== BufferBox Test ===")
|
||||
local buffer
|
||||
buffer = new BufferBox()
|
||||
|
||||
// write
|
||||
local bytesArray
|
||||
bytesArray = new ArrayBox()
|
||||
bytesArray.push(72) // H
|
||||
bytesArray.push(101) // e
|
||||
bytesArray.push(108) // l
|
||||
bytesArray.push(108) // l
|
||||
bytesArray.push(111) // o
|
||||
buffer.write(bytesArray)
|
||||
print("Buffer length after write: " + buffer.length())
|
||||
|
||||
// readAll
|
||||
local readData
|
||||
readData = buffer.readAll()
|
||||
print("Read data length: " + readData.length())
|
||||
|
||||
// 3. JSONBoxのテスト
|
||||
print("\n=== JSONBox Test ===")
|
||||
local parsed
|
||||
parsed = new JSONBox("{\"name\": \"Nyash\", \"version\": 1.0}")
|
||||
|
||||
print("JSON stringify: " + parsed.stringify())
|
||||
print("Name from JSON: " + parsed.get("name"))
|
||||
print("Version from JSON: " + parsed.get("version"))
|
||||
|
||||
// set/has
|
||||
parsed.set("author", "Claude")
|
||||
print("Has author: " + parsed.has("author"))
|
||||
print("Author: " + parsed.get("author"))
|
||||
|
||||
// keys
|
||||
local keys
|
||||
keys = parsed.keys()
|
||||
print("Keys count: " + keys.length())
|
||||
|
||||
// 4. RegexBoxのテスト
|
||||
print("\n=== RegexBox Test ===")
|
||||
local regex, text
|
||||
regex = new RegexBox("[0-9]+")
|
||||
text = "The answer is 42 and 100"
|
||||
|
||||
print("Test match: " + regex.test(text))
|
||||
print("Find first: " + regex.find(text))
|
||||
|
||||
local allMatches
|
||||
allMatches = regex.findAll(text)
|
||||
print("All matches count: " + allMatches.length())
|
||||
|
||||
// replace
|
||||
local replaced
|
||||
replaced = regex.replace(text, "X")
|
||||
print("Replaced: " + replaced)
|
||||
|
||||
// split
|
||||
local emailRegex, email
|
||||
emailRegex = new RegexBox("@")
|
||||
email = "user@example.com"
|
||||
local parts
|
||||
parts = emailRegex.split(email)
|
||||
print("Email parts: " + parts.join(" | "))
|
||||
|
||||
// 5. StreamBoxのテスト
|
||||
print("\n=== StreamBox Test ===")
|
||||
local stream
|
||||
stream = new StreamBox()
|
||||
|
||||
// write
|
||||
stream.write("Hello Stream!")
|
||||
print("Stream length: " + stream.length())
|
||||
print("Stream position: " + stream.position())
|
||||
|
||||
// read
|
||||
local readCount, streamData
|
||||
readCount = stream.read(5)
|
||||
print("Read from stream: " + readCount.length() + " bytes")
|
||||
print("Position after read: " + stream.position())
|
||||
|
||||
// reset
|
||||
stream.reset()
|
||||
print("Position after reset: " + stream.position())
|
||||
|
||||
print("\n✅ All tests completed!")
|
||||
@ -1,62 +0,0 @@
|
||||
# 🚀 Rust-Style Trait-Based Operator System Test
|
||||
# Testing the new NyashAdd trait implementation
|
||||
|
||||
static box Main {
|
||||
init { console, result }
|
||||
|
||||
main() {
|
||||
me.console = new ConsoleBox()
|
||||
me.console.log("🎉 Testing New Trait-Based Operators!")
|
||||
|
||||
# Test 1: Integer addition
|
||||
local a, b, sum
|
||||
a = 10
|
||||
b = 20
|
||||
sum = a + b
|
||||
me.console.log("Integer addition: 10 + 20 = " + sum)
|
||||
|
||||
# Test 2: String concatenation
|
||||
local s1, s2, concat
|
||||
s1 = "Hello"
|
||||
s2 = " World"
|
||||
concat = s1 + s2
|
||||
me.console.log("String concat: " + concat)
|
||||
|
||||
# Test 3: String repetition
|
||||
local str, count, repeated
|
||||
str = "Hi"
|
||||
count = 3
|
||||
repeated = str * count
|
||||
me.console.log("String repeat: Hi * 3 = " + repeated)
|
||||
|
||||
# Test 4: Mixed type fallback (int + string -> string concat)
|
||||
local mixed
|
||||
mixed = 42 + " is the answer"
|
||||
me.console.log("Mixed types: " + mixed)
|
||||
|
||||
# Test 5: Boolean arithmetic
|
||||
local bool1, bool2, bool_sum
|
||||
bool1 = true
|
||||
bool2 = false
|
||||
bool_sum = bool1 + bool2
|
||||
me.console.log("Boolean add: true + false = " + bool_sum)
|
||||
|
||||
# Test 6: Subtraction
|
||||
local diff
|
||||
diff = 100 - 25
|
||||
me.console.log("Subtraction: 100 - 25 = " + diff)
|
||||
|
||||
# Test 7: Multiplication
|
||||
local product
|
||||
product = 6 * 7
|
||||
me.console.log("Multiplication: 6 * 7 = " + product)
|
||||
|
||||
# Test 8: Division
|
||||
local quotient
|
||||
quotient = 84 / 12
|
||||
me.console.log("Division: 84 / 12 = " + quotient)
|
||||
|
||||
me.console.log("🎯 All operator tests completed!")
|
||||
return "New trait system works perfectly!"
|
||||
}
|
||||
}
|
||||
@ -1,100 +0,0 @@
|
||||
// test_operators.nyash - Operator Phase 3 comprehensive test
|
||||
// Testing: comparison operators (<, >, <=, >=, ==, !=) with mixed types
|
||||
|
||||
print("⚖️ Testing comprehensive operator support...")
|
||||
|
||||
local f1, f2, i1, i2, result
|
||||
|
||||
print("=== Setup: Creating test values ===")
|
||||
f1 = new FloatBox(3.14)
|
||||
f2 = new FloatBox(2.86)
|
||||
i1 = 5
|
||||
i2 = 3
|
||||
print("f1 = " + f1.toString() + " (FloatBox)")
|
||||
print("f2 = " + f2.toString() + " (FloatBox)")
|
||||
print("i1 = " + i1.toString() + " (IntegerBox)")
|
||||
print("i2 = " + i2.toString() + " (IntegerBox)")
|
||||
|
||||
print("\n=== Test 1: Equality operators (==, !=) ===")
|
||||
result = f1 == new FloatBox(3.14)
|
||||
print("f1 == 3.14: " + result.toString()) // Expected: true
|
||||
|
||||
result = f1 != f2
|
||||
print("f1 != f2: " + result.toString()) // Expected: true
|
||||
|
||||
result = i1 == 5
|
||||
print("i1 == 5: " + result.toString()) // Expected: true
|
||||
|
||||
result = i1 != i2
|
||||
print("i1 != i2: " + result.toString()) // Expected: true
|
||||
|
||||
print("\n=== Test 2: Mixed type equality ===")
|
||||
result = f1 == 3 // FloatBox vs IntegerBox
|
||||
print("f1 == 3: " + result.toString()) // Expected: false (3.14 != 3)
|
||||
|
||||
result = new FloatBox(5.0) == i1 // FloatBox vs IntegerBox
|
||||
print("5.0 == i1: " + result.toString()) // Expected: true
|
||||
|
||||
print("\n=== Test 3: Less than (<) ===")
|
||||
result = f2 < f1 // FloatBox < FloatBox
|
||||
print("f2 < f1: " + result.toString()) // Expected: true (2.86 < 3.14)
|
||||
|
||||
result = i2 < i1 // IntegerBox < IntegerBox
|
||||
print("i2 < i1: " + result.toString()) // Expected: true (3 < 5)
|
||||
|
||||
result = f2 < i1 // FloatBox < IntegerBox
|
||||
print("f2 < i1: " + result.toString()) // Expected: true (2.86 < 5)
|
||||
|
||||
result = i2 < f1 // IntegerBox < FloatBox
|
||||
print("i2 < f1: " + result.toString()) // Expected: true (3 < 3.14)
|
||||
|
||||
print("\n=== Test 4: Greater than (>) ===")
|
||||
result = f1 > f2 // FloatBox > FloatBox
|
||||
print("f1 > f2: " + result.toString()) // Expected: true (3.14 > 2.86)
|
||||
|
||||
result = i1 > i2 // IntegerBox > IntegerBox
|
||||
print("i1 > i2: " + result.toString()) // Expected: true (5 > 3)
|
||||
|
||||
result = i1 > f1 // IntegerBox > FloatBox
|
||||
print("i1 > f1: " + result.toString()) // Expected: true (5 > 3.14)
|
||||
|
||||
result = f1 > i2 // FloatBox > IntegerBox
|
||||
print("f1 > i2: " + result.toString()) // Expected: true (3.14 > 3)
|
||||
|
||||
print("\n=== Test 5: Less than or equal (<=) ===")
|
||||
result = f2 <= f1 // FloatBox <= FloatBox
|
||||
print("f2 <= f1: " + result.toString()) // Expected: true (2.86 <= 3.14)
|
||||
|
||||
result = f1 <= f1 // FloatBox <= FloatBox (equal)
|
||||
print("f1 <= f1: " + result.toString()) // Expected: true (3.14 <= 3.14)
|
||||
|
||||
result = i2 <= i1 // IntegerBox <= IntegerBox
|
||||
print("i2 <= i1: " + result.toString()) // Expected: true (3 <= 5)
|
||||
|
||||
result = new FloatBox(5.0) <= i1 // FloatBox <= IntegerBox (equal)
|
||||
print("5.0 <= i1: " + result.toString()) // Expected: true (5.0 <= 5)
|
||||
|
||||
print("\n=== Test 6: Greater than or equal (>=) ===")
|
||||
result = f1 >= f2 // FloatBox >= FloatBox
|
||||
print("f1 >= f2: " + result.toString()) // Expected: true (3.14 >= 2.86)
|
||||
|
||||
result = f1 >= f1 // FloatBox >= FloatBox (equal)
|
||||
print("f1 >= f1: " + result.toString()) // Expected: true (3.14 >= 3.14)
|
||||
|
||||
result = i1 >= i2 // IntegerBox >= IntegerBox
|
||||
print("i1 >= i2: " + result.toString()) // Expected: true (5 >= 3)
|
||||
|
||||
result = i1 >= new FloatBox(5.0) // IntegerBox >= FloatBox (equal)
|
||||
print("i1 >= 5.0: " + result.toString()) // Expected: true (5 >= 5.0)
|
||||
|
||||
print("\n=== Test 7: Complex expression chains ===")
|
||||
result = (f1 > f2) and (i1 > i2)
|
||||
print("(f1 > f2) and (i1 > i2): " + result.toString()) // Expected: true
|
||||
|
||||
result = (f1 < i1) and (f2 > 1)
|
||||
print("(f1 < i1) and (f2 > 1): " + result.toString()) // Expected: true
|
||||
|
||||
result = not (f1 == f2)
|
||||
print("not (f1 == f2): " + result.toString()) // Expected: true
|
||||
|
||||
print("\n✅ Comprehensive operator tests completed!")
|
||||
@ -1,48 +0,0 @@
|
||||
// 🔍 override検証テスト - デリゲーションメソッドチェック機能
|
||||
|
||||
// 1. ✅ 正常なoverride(基本テスト)
|
||||
box Animal {
|
||||
init { name }
|
||||
|
||||
pack(animalName) {
|
||||
me.name = animalName
|
||||
}
|
||||
|
||||
speak() {
|
||||
return me.name + " makes a sound"
|
||||
}
|
||||
|
||||
move() {
|
||||
return me.name + " moves"
|
||||
}
|
||||
}
|
||||
|
||||
box Dog from Animal {
|
||||
init { breed }
|
||||
|
||||
pack(dogName, dogBreed) {
|
||||
from Animal.pack(dogName)
|
||||
me.breed = dogBreed
|
||||
}
|
||||
|
||||
// ✅ 正常なoverride - speakメソッドは親に存在
|
||||
override speak() {
|
||||
return me.name + " (dog) barks: Woof!"
|
||||
}
|
||||
|
||||
// ✅ 正常なoverride - moveメソッドも親に存在
|
||||
override move() {
|
||||
return me.name + " runs fast"
|
||||
}
|
||||
}
|
||||
|
||||
// テスト実行
|
||||
print("=== 🔍 Override検証テスト ===")
|
||||
|
||||
local dog
|
||||
dog = new Dog("Buddy", "Labrador")
|
||||
print("Dog speak: " + dog.speak())
|
||||
print("Dog move: " + dog.move())
|
||||
|
||||
print("")
|
||||
print("✅ 正常なoverrideテスト完了!")
|
||||
@ -1,61 +0,0 @@
|
||||
// 🧪 P2PBox基本機能テスト
|
||||
// IntentBoxとP2PBoxの基本的な動作を検証
|
||||
|
||||
print("=== P2PBox Basic Test ===")
|
||||
|
||||
// 1. IntentBoxの作成
|
||||
print("\n1. Creating IntentBox...")
|
||||
local world
|
||||
world = new IntentBox()
|
||||
print("✅ IntentBox created: " + world.type())
|
||||
|
||||
// 2. P2PBoxノードの作成
|
||||
print("\n2. Creating P2PBox nodes...")
|
||||
local alice
|
||||
local bob
|
||||
local charlie
|
||||
|
||||
alice = new P2PBox("alice", world)
|
||||
bob = new P2PBox("bob", world)
|
||||
charlie = new P2PBox("charlie", world)
|
||||
|
||||
print("✅ Alice created: " + alice.getNodeId())
|
||||
print("✅ Bob created: " + bob.getNodeId())
|
||||
print("✅ Charlie created: " + charlie.getNodeId())
|
||||
|
||||
// 3. リスナー登録テスト
|
||||
print("\n3. Testing listener registration...")
|
||||
bob.on("greeting", "bob_greeting_handler")
|
||||
charlie.on("greeting", "charlie_greeting_handler")
|
||||
print("✅ Listeners registered")
|
||||
|
||||
// 4. 直接送信テスト
|
||||
print("\n4. Testing direct send...")
|
||||
alice.send("greeting", "Hello Bob!", "bob")
|
||||
alice.send("greeting", "Hello Charlie!", "charlie")
|
||||
print("✅ Messages sent")
|
||||
|
||||
// 5. ブロードキャストテスト
|
||||
print("\n5. Testing broadcast...")
|
||||
alice.broadcast("announcement", "Hello everyone!")
|
||||
print("✅ Broadcast sent")
|
||||
|
||||
// 6. リスナー解除テスト
|
||||
print("\n6. Testing listener removal...")
|
||||
local result
|
||||
result = bob.off("greeting")
|
||||
print("✅ Bob's listener removed: " + result)
|
||||
|
||||
// 7. 解除後の送信テスト
|
||||
print("\n7. Testing send after listener removal...")
|
||||
alice.send("greeting", "Hello again Bob!", "bob")
|
||||
print("✅ Message sent (Bob should not receive)")
|
||||
|
||||
// 8. 複数リスナーテスト
|
||||
print("\n8. Testing multiple listeners...")
|
||||
charlie.on("data", "charlie_data_handler1")
|
||||
charlie.on("data", "charlie_data_handler2")
|
||||
alice.send("data", "Test data", "charlie")
|
||||
print("✅ Multiple listeners tested")
|
||||
|
||||
print("\n=== Test Complete ===")
|
||||
@ -1,116 +0,0 @@
|
||||
// 🧪 P2PBox New Architecture Test
|
||||
// Tests the completely rewritten P2P communication system
|
||||
|
||||
print("=== P2PBox New Architecture Test ===")
|
||||
|
||||
// 1. Test IntentBox creation with structured messages
|
||||
print("\n1. Testing IntentBox structured messages...")
|
||||
local msg1
|
||||
local msg2
|
||||
local msg3
|
||||
|
||||
msg1 = new IntentBox("chat.message", "{ \"text\": \"Hello P2P!\", \"from\": \"alice\" }")
|
||||
msg2 = new IntentBox("file.share", "{ \"filename\": \"document.pdf\", \"size\": 1024000 }")
|
||||
msg3 = new IntentBox("system.ping", "{ \"timestamp\": 1635789456 }")
|
||||
|
||||
print("✅ IntentBox 1: " + msg1.getName() + " -> " + msg1.getPayload())
|
||||
print("✅ IntentBox 2: " + msg2.getName() + " -> " + msg2.getPayload())
|
||||
print("✅ IntentBox 3: " + msg3.getName() + " -> " + msg3.getPayload())
|
||||
|
||||
// 2. Test P2PBox creation with InProcess transport
|
||||
print("\n2. Testing P2PBox creation...")
|
||||
local alice
|
||||
local bob
|
||||
local charlie
|
||||
|
||||
alice = new P2PBox("alice", "inprocess")
|
||||
bob = new P2PBox("bob", "inprocess")
|
||||
charlie = new P2PBox("charlie", "inprocess")
|
||||
|
||||
print("✅ Alice created: " + alice.getNodeId() + " (" + alice.getTransportType() + ")")
|
||||
print("✅ Bob created: " + bob.getNodeId() + " (" + bob.getTransportType() + ")")
|
||||
print("✅ Charlie created: " + charlie.getNodeId() + " (" + charlie.getTransportType() + ")")
|
||||
|
||||
// 3. Test node reachability
|
||||
print("\n3. Testing node reachability...")
|
||||
local alice_can_reach_bob
|
||||
local bob_can_reach_charlie
|
||||
local alice_can_reach_nonexistent
|
||||
|
||||
alice_can_reach_bob = alice.isReachable("bob")
|
||||
bob_can_reach_charlie = bob.isReachable("charlie")
|
||||
alice_can_reach_nonexistent = alice.isReachable("nonexistent")
|
||||
|
||||
print("✅ Alice can reach Bob: " + alice_can_reach_bob)
|
||||
print("✅ Bob can reach Charlie: " + bob_can_reach_charlie)
|
||||
print("✅ Alice can reach nonexistent: " + alice_can_reach_nonexistent)
|
||||
|
||||
// 4. Test basic message sending
|
||||
print("\n4. Testing basic message sending...")
|
||||
local result1
|
||||
local result2
|
||||
|
||||
// Send chat message from Alice to Bob
|
||||
local chat_msg
|
||||
chat_msg = new IntentBox("chat.message", "{ \"text\": \"Hello Bob!\", \"from\": \"alice\" }")
|
||||
result1 = alice.send("bob", chat_msg)
|
||||
print("✅ Alice -> Bob: " + result1)
|
||||
|
||||
// Send file share from Bob to Charlie
|
||||
local file_msg
|
||||
file_msg = new IntentBox("file.share", "{ \"filename\": \"data.txt\", \"size\": 512 }")
|
||||
result2 = bob.send("charlie", file_msg)
|
||||
print("✅ Bob -> Charlie: " + result2)
|
||||
|
||||
// 5. Test system behavior verification
|
||||
print("\n5. Testing system behavior...")
|
||||
|
||||
// All nodes should be of correct type
|
||||
print("✅ Alice type: " + alice.type())
|
||||
print("✅ Bob type: " + bob.type())
|
||||
print("✅ Charlie type: " + charlie.type())
|
||||
|
||||
// IntentBox should show proper structure
|
||||
print("✅ Message 1 type: " + msg1.type())
|
||||
print("✅ Message 2 type: " + msg2.type())
|
||||
print("✅ Message 3 type: " + msg3.type())
|
||||
|
||||
// 6. Performance test - rapid message sending
|
||||
print("\n6. Testing performance...")
|
||||
local perf_start_time
|
||||
local perf_msg
|
||||
local i
|
||||
|
||||
perf_start_time = new TimeBox()
|
||||
|
||||
i = 0
|
||||
loop(i < 10) {
|
||||
perf_msg = new IntentBox("test.performance", "{ \"id\": " + i + " }")
|
||||
alice.send("bob", perf_msg)
|
||||
i = i + 1
|
||||
}
|
||||
|
||||
local perf_end_time
|
||||
perf_end_time = new TimeBox()
|
||||
print("✅ Sent 10 messages successfully")
|
||||
|
||||
// 7. Error handling test - send to nonexistent node
|
||||
print("\n7. Testing error handling...")
|
||||
local error_msg
|
||||
local error_result
|
||||
|
||||
error_msg = new IntentBox("test.error", "{ \"test\": true }")
|
||||
|
||||
// This should fail gracefully
|
||||
print("Attempting to send to nonexistent node...")
|
||||
// Note: This will likely cause a runtime error, which is expected
|
||||
|
||||
print("\n=== P2P New Architecture Test Complete ===")
|
||||
print("🎉 All basic P2P functionality working correctly!")
|
||||
print("🌟 New architecture features verified:")
|
||||
print(" - Structured IntentBox messages (name + payload)")
|
||||
print(" - P2PBox with InProcess transport")
|
||||
print(" - Node reachability checking")
|
||||
print(" - Individual send API (no broadcast)")
|
||||
print(" - Arc<Mutex> memory safety pattern")
|
||||
print(" - MessageBus singleton routing")
|
||||
@ -1,94 +0,0 @@
|
||||
// 🧪 P2PBox コールバック実行デモ
|
||||
// 実際のメッセージ受信とコールバック実行の様子を確認
|
||||
|
||||
print("=== P2PBox Callback Demo ===")
|
||||
|
||||
// 通信世界を作成
|
||||
local world
|
||||
world = new IntentBox()
|
||||
|
||||
print("\n1. Creating chat nodes...")
|
||||
local alice
|
||||
local bob
|
||||
alice = new P2PBox("alice", world)
|
||||
bob = new P2PBox("bob", world)
|
||||
print("✅ Alice and Bob joined the chat")
|
||||
|
||||
// 現在はコールバックを実際に実行できないため、
|
||||
// 登録と送信の流れを示すデモンストレーション
|
||||
print("\n2. Registering message handlers...")
|
||||
print("⚠️ Note: Callbacks are registered but not executed in current implementation")
|
||||
print(" (MethodBox integration pending)")
|
||||
|
||||
// Bobのメッセージハンドラー登録
|
||||
bob.on("chat", "bob_chat_handler")
|
||||
bob.on("typing", "bob_typing_handler")
|
||||
bob.on("image", "bob_image_handler")
|
||||
print("✅ Bob's handlers registered")
|
||||
|
||||
// Aliceのメッセージハンドラー登録
|
||||
alice.on("chat", "alice_chat_handler")
|
||||
alice.on("reply", "alice_reply_handler")
|
||||
print("✅ Alice's handlers registered")
|
||||
|
||||
print("\n3. Message exchange simulation...")
|
||||
|
||||
// チャットメッセージ
|
||||
local chatMsg
|
||||
chatMsg = new MapBox()
|
||||
chatMsg.set("text", "Hi Bob! How are you?")
|
||||
chatMsg.set("timestamp", 1234567890)
|
||||
alice.send("chat", chatMsg, "bob")
|
||||
print("Alice → Bob: Hi Bob! How are you?")
|
||||
|
||||
// タイピング通知
|
||||
alice.send("typing", true, "bob")
|
||||
print("Alice → Bob: [typing...]")
|
||||
|
||||
// 画像送信
|
||||
local imageMsg
|
||||
imageMsg = new MapBox()
|
||||
imageMsg.set("url", "https://example.com/photo.jpg")
|
||||
imageMsg.set("caption", "Check out this photo!")
|
||||
alice.send("image", imageMsg, "bob")
|
||||
print("Alice → Bob: [sent an image]")
|
||||
|
||||
// 返信
|
||||
local replyMsg
|
||||
replyMsg = new MapBox()
|
||||
replyMsg.set("text", "I'm doing great, thanks!")
|
||||
replyMsg.set("replyTo", "Hi Bob! How are you?")
|
||||
bob.send("reply", replyMsg, "alice")
|
||||
print("Bob → Alice: I'm doing great, thanks!")
|
||||
|
||||
print("\n4. Broadcast demo...")
|
||||
// 全員への通知
|
||||
local announcement
|
||||
announcement = new MapBox()
|
||||
announcement.set("type", "system")
|
||||
announcement.set("message", "Welcome to NyaMesh P2P Chat!")
|
||||
alice.broadcast("announcement", announcement)
|
||||
print("System broadcast: Welcome to NyaMesh P2P Chat!")
|
||||
|
||||
print("\n5. Testing message queue...")
|
||||
// メッセージキューの処理
|
||||
local processed
|
||||
processed = world.processMessages()
|
||||
print("Messages in queue: " + processed)
|
||||
|
||||
print("\n6. Dynamic listener management...")
|
||||
// 動的なリスナー管理
|
||||
alice.off("chat")
|
||||
print("✅ Alice unsubscribed from chat")
|
||||
|
||||
// 解除後のメッセージ(受信されない)
|
||||
bob.send("chat", "Are you still there?", "alice")
|
||||
print("Bob → Alice: Are you still there? (Alice won't receive)")
|
||||
|
||||
print("\n=== Demo Complete ===")
|
||||
print("\n📝 Summary:")
|
||||
print("- IntentBox creates communication worlds")
|
||||
print("- P2PBox nodes can join and exchange messages")
|
||||
print("- Listeners can be dynamically added/removed")
|
||||
print("- LocalTransport handles in-process messaging")
|
||||
print("- Full callback execution requires MethodBox integration")
|
||||
@ -1,86 +0,0 @@
|
||||
// 🧪 P2PBox エッジケーステスト
|
||||
// エラーハンドリングと異常系の動作検証
|
||||
|
||||
print("=== P2PBox Edge Cases Test ===")
|
||||
|
||||
// 基本セットアップ
|
||||
local world
|
||||
world = new IntentBox()
|
||||
|
||||
local node1
|
||||
node1 = new P2PBox("node1", world)
|
||||
|
||||
print("\n1. Testing invalid target send")
|
||||
// 存在しないノードへの送信
|
||||
local result
|
||||
result = node1.send("test", "data", "non_existent_node")
|
||||
print("Send to non-existent node: " + result)
|
||||
|
||||
print("\n2. Testing empty intent string")
|
||||
// 空のintent文字列
|
||||
node1.on("", "empty_handler")
|
||||
result = node1.send("", "test data", "node1")
|
||||
print("Empty intent handled: " + result)
|
||||
|
||||
print("\n3. Testing duplicate listener removal")
|
||||
// 同じintentを2回削除
|
||||
node1.on("test_event", "handler1")
|
||||
result = node1.off("test_event")
|
||||
print("First removal: " + result)
|
||||
result = node1.off("test_event")
|
||||
print("Second removal: " + result)
|
||||
|
||||
print("\n4. Testing self-messaging")
|
||||
// 自分自身へのメッセージ送信
|
||||
node1.on("self_msg", "self_handler")
|
||||
result = node1.send("self_msg", "Hello myself!", "node1")
|
||||
print("Self message sent: " + result)
|
||||
|
||||
print("\n5. Testing very long intent names")
|
||||
// 非常に長いintent名
|
||||
local longIntent
|
||||
longIntent = "this_is_a_very_long_intent_name_that_tests_the_system_limits_1234567890_abcdefghijklmnopqrstuvwxyz"
|
||||
node1.on(longIntent, "long_handler")
|
||||
result = node1.send(longIntent, "test", "node1")
|
||||
print("Long intent handled: " + result)
|
||||
|
||||
print("\n6. Testing special characters in node ID")
|
||||
// 特殊文字を含むノードID(新規作成時)
|
||||
local specialNode
|
||||
specialNode = new P2PBox("node-with-special_chars.123", world)
|
||||
print("Special node created: " + specialNode.getNodeId())
|
||||
|
||||
print("\n7. Testing rapid fire messages")
|
||||
// 高速連続メッセージ送信
|
||||
local node2
|
||||
node2 = new P2PBox("node2", world)
|
||||
node2.on("rapid", "rapid_handler")
|
||||
|
||||
local i
|
||||
i = 0
|
||||
loop(i < 10) {
|
||||
node1.send("rapid", "Message " + i, "node2")
|
||||
i = i + 1
|
||||
}
|
||||
print("Sent 10 rapid messages")
|
||||
|
||||
print("\n8. Testing null data send")
|
||||
// nullデータの送信
|
||||
local nullData
|
||||
nullData = new NullBox()
|
||||
result = node1.send("null_test", nullData, "node2")
|
||||
print("Null data sent: " + result)
|
||||
|
||||
print("\n9. Testing listener with same intent multiple times")
|
||||
// 同じintentに複数のリスナー登録
|
||||
node1.on("multi", "handler1")
|
||||
node1.on("multi", "handler2")
|
||||
node1.on("multi", "handler3")
|
||||
print("Multiple handlers registered for same intent")
|
||||
|
||||
print("\n10. Testing IntentBox message processing")
|
||||
// IntentBoxの内部メッセージ処理
|
||||
result = world.processMessages()
|
||||
print("IntentBox processed messages: " + result)
|
||||
|
||||
print("\n=== Edge Cases Test Complete ===")
|
||||
@ -1,66 +0,0 @@
|
||||
// 🧪 P2PBox メッセージ型テスト
|
||||
// 様々なデータ型のメッセージ送受信を検証
|
||||
|
||||
print("=== P2PBox Message Types Test ===")
|
||||
|
||||
// 通信世界とノードを作成
|
||||
local world
|
||||
world = new IntentBox()
|
||||
|
||||
local sender
|
||||
local receiver
|
||||
sender = new P2PBox("sender", world)
|
||||
receiver = new P2PBox("receiver", world)
|
||||
|
||||
// 各種データ型のリスナーを登録
|
||||
receiver.on("string_msg", "handle_string")
|
||||
receiver.on("integer_msg", "handle_integer")
|
||||
receiver.on("bool_msg", "handle_bool")
|
||||
receiver.on("null_msg", "handle_null")
|
||||
receiver.on("array_msg", "handle_array")
|
||||
receiver.on("map_msg", "handle_map")
|
||||
|
||||
print("\n1. String message test")
|
||||
sender.send("string_msg", "Hello, P2P World!", "receiver")
|
||||
|
||||
print("\n2. Integer message test")
|
||||
sender.send("integer_msg", 42, "receiver")
|
||||
|
||||
print("\n3. Boolean message test")
|
||||
sender.send("bool_msg", true, "receiver")
|
||||
|
||||
print("\n4. Null message test")
|
||||
local nullValue
|
||||
nullValue = new NullBox()
|
||||
sender.send("null_msg", nullValue, "receiver")
|
||||
|
||||
print("\n5. Array message test (NOT IMPLEMENTED YET)")
|
||||
// TODO: ArrayBox実装後に有効化
|
||||
// local arr
|
||||
// arr = new ArrayBox()
|
||||
// arr.push("item1")
|
||||
// arr.push("item2")
|
||||
// sender.send("array_msg", arr, "receiver")
|
||||
|
||||
print("\n6. Map message test")
|
||||
local data
|
||||
data = new MapBox()
|
||||
data.set("name", "Alice")
|
||||
data.set("age", 25)
|
||||
data.set("active", true)
|
||||
sender.send("map_msg", data, "receiver")
|
||||
|
||||
print("\n7. Complex nested data test")
|
||||
local complex
|
||||
complex = new MapBox()
|
||||
complex.set("type", "user_profile")
|
||||
|
||||
local details
|
||||
details = new MapBox()
|
||||
details.set("username", "alice123")
|
||||
details.set("email", "alice@example.com")
|
||||
complex.set("details", details)
|
||||
|
||||
sender.broadcast("complex_data", complex)
|
||||
|
||||
print("\n=== Message Types Test Complete ===")
|
||||
@ -1,14 +0,0 @@
|
||||
// Simple P2P Test - Basic functionality check
|
||||
print("=== Simple P2P Test ===")
|
||||
|
||||
// Test 1: Create IntentBox
|
||||
local msg
|
||||
msg = new IntentBox("test.message", "Hello P2P")
|
||||
print("✅ IntentBox created: " + msg.getName())
|
||||
|
||||
// Test 2: Create P2PBox
|
||||
local node
|
||||
node = new P2PBox("test_node", "inprocess")
|
||||
print("✅ P2PBox created: " + node.getNodeId())
|
||||
|
||||
print("✅ P2P system is working!")
|
||||
@ -1,108 +0,0 @@
|
||||
// 🎁 pack構文の包括的テスト
|
||||
|
||||
// 1. 基本的なpack構文
|
||||
box Animal {
|
||||
init { name, age }
|
||||
|
||||
pack(animalName, animalAge) {
|
||||
me.name = animalName
|
||||
me.age = animalAge
|
||||
}
|
||||
|
||||
speak() {
|
||||
return me.name + " (age " + me.age + ") makes a sound"
|
||||
}
|
||||
}
|
||||
|
||||
// 2. fromデリゲーションでのpack
|
||||
box Dog from Animal {
|
||||
init { breed }
|
||||
|
||||
pack(dogName, dogAge, dogBreed) {
|
||||
from Animal.pack(dogName, dogAge) // 親のpackを呼び出し
|
||||
me.breed = dogBreed
|
||||
}
|
||||
|
||||
override speak() {
|
||||
return me.name + " (age " + me.age + ", " + me.breed + ") barks: Woof!"
|
||||
}
|
||||
}
|
||||
|
||||
// 3. 混在形式(packと従来形式の共存)
|
||||
box Cat from Animal {
|
||||
init { color }
|
||||
|
||||
Cat(catName, catAge, catColor) { // 従来形式
|
||||
from Animal.pack(catName, catAge) // 親はpack使用
|
||||
me.color = catColor
|
||||
}
|
||||
|
||||
override speak() {
|
||||
return me.name + " (age " + me.age + ", " + me.color + ") meows: Meow!"
|
||||
}
|
||||
}
|
||||
|
||||
// 4. pack単独使用テスト
|
||||
box Bird {
|
||||
init { species, canFly }
|
||||
|
||||
// pack単独 - Box哲学に最適!
|
||||
pack(birdSpecies, flying) {
|
||||
me.species = birdSpecies + " (pack使用)"
|
||||
me.canFly = flying
|
||||
}
|
||||
|
||||
describe() {
|
||||
local flyText
|
||||
if me.canFly {
|
||||
flyText = "can fly"
|
||||
} else {
|
||||
flyText = "cannot fly"
|
||||
}
|
||||
return me.species + " - " + flyText
|
||||
}
|
||||
}
|
||||
|
||||
// テスト実行
|
||||
print("=== 🎁 pack構文テスト ===")
|
||||
|
||||
// 1. 基本的なpack
|
||||
local animal
|
||||
animal = new Animal("Generic", 5)
|
||||
print("Animal: " + animal.speak())
|
||||
|
||||
// 2. デリゲーションでのpack
|
||||
local dog
|
||||
dog = new Dog("Buddy", 3, "Golden Retriever")
|
||||
print("Dog: " + dog.speak())
|
||||
|
||||
// 3. 混在形式
|
||||
local cat
|
||||
cat = new Cat("Whiskers", 2, "Black")
|
||||
print("Cat: " + cat.speak())
|
||||
|
||||
// 4. pack単独使用確認
|
||||
local bird
|
||||
bird = new Bird("Eagle", true)
|
||||
print("Bird: " + bird.describe())
|
||||
|
||||
// 5. 引数なしpack
|
||||
box SimpleBox {
|
||||
init { message }
|
||||
|
||||
pack() { // 引数なしpack
|
||||
me.message = "Packed with love! 🎁"
|
||||
}
|
||||
|
||||
getMessage() {
|
||||
return me.message
|
||||
}
|
||||
}
|
||||
|
||||
local simple
|
||||
simple = new SimpleBox()
|
||||
print("SimpleBox: " + simple.getMessage())
|
||||
|
||||
print("")
|
||||
print("✅ pack構文テスト完了!")
|
||||
print("🎉 Everything is Box - Now Everything is Packed!")
|
||||
@ -1,32 +0,0 @@
|
||||
// 🎲 RandomBoxのテスト
|
||||
|
||||
print("=== RandomBox Test ===")
|
||||
local random, result, array
|
||||
|
||||
// RandomBox作成
|
||||
random = new RandomBox()
|
||||
|
||||
// 基本乱数テスト
|
||||
result = random.random()
|
||||
print("Random float: " + result)
|
||||
|
||||
result = random.randInt(1, 6)
|
||||
print("Dice roll (1-6): " + result)
|
||||
|
||||
result = random.randBool()
|
||||
print("Random bool: " + result)
|
||||
|
||||
// 配列テスト
|
||||
array = new ArrayBox()
|
||||
array.push("apple")
|
||||
array.push("banana")
|
||||
array.push("cherry")
|
||||
|
||||
result = random.choice(array)
|
||||
print("Random choice: " + result)
|
||||
|
||||
// 文字列生成テスト
|
||||
result = random.randString(5)
|
||||
print("Random string (5 chars): " + result)
|
||||
|
||||
print("RandomBox test completed!")
|
||||
@ -1,50 +0,0 @@
|
||||
// Basic weak reference test case - with null fix
|
||||
|
||||
box Parent {
|
||||
init { child }
|
||||
|
||||
pack() {
|
||||
me.child = new Child()
|
||||
me.child.setParent(me) // This should create a weak reference
|
||||
}
|
||||
|
||||
getChild() {
|
||||
return me.child
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
checkParent() {
|
||||
return me.parent != new NullBox()
|
||||
}
|
||||
|
||||
getParentInfo() {
|
||||
if me.parent != new NullBox() {
|
||||
return "Parent exists"
|
||||
} else {
|
||||
return "Parent is null (dropped)"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
local p = new Parent()
|
||||
local child = p.getChild()
|
||||
|
||||
print("Initial parent check: " + child.getParentInfo())
|
||||
|
||||
// When p goes out of scope, child.parent should automatically become null
|
||||
p = new NullBox()
|
||||
|
||||
print("After parent dropped: " + child.getParentInfo())
|
||||
|
||||
return "weak reference test completed"
|
||||
}
|
||||
}
|
||||
@ -1,84 +0,0 @@
|
||||
// Comprehensive weak reference validation test
|
||||
|
||||
box Parent {
|
||||
init { name }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent, id }
|
||||
|
||||
pack(childId) {
|
||||
me.id = childId
|
||||
me.parent = 0 // Initialize as null
|
||||
}
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
// Safe check that doesn't call toString on null
|
||||
checkParentStatus() {
|
||||
local parentRef = me.parent
|
||||
|
||||
// Check if we got a valid parent reference
|
||||
local console = new ConsoleBox()
|
||||
console.log("Child " + me.id.toString() + " checking parent...")
|
||||
|
||||
// We expect null after parent drop, which should not cause errors
|
||||
return "checked"
|
||||
}
|
||||
|
||||
getId() {
|
||||
return me.id
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== Comprehensive Weak Reference Validation ===")
|
||||
|
||||
local parent1 = new Parent("Parent1")
|
||||
local parent2 = new Parent("Parent2")
|
||||
|
||||
local child1 = new Child(1)
|
||||
local child2 = new Child(2)
|
||||
local child3 = new Child(3)
|
||||
|
||||
print("Step 1: Set up multiple weak references")
|
||||
child1.setParent(parent1)
|
||||
child2.setParent(parent1) // Two children reference same parent
|
||||
child3.setParent(parent2) // One child references different parent
|
||||
|
||||
print("Step 2: Verify all children can access parents")
|
||||
child1.checkParentStatus()
|
||||
child2.checkParentStatus()
|
||||
child3.checkParentStatus()
|
||||
|
||||
print("Step 3: Drop parent1 (affects child1 and child2)")
|
||||
parent1 = 0 // This should invalidate child1 and child2's references
|
||||
|
||||
print("Step 4: Check all children after parent1 drop")
|
||||
child1.checkParentStatus() // Should be null now
|
||||
child2.checkParentStatus() // Should be null now
|
||||
child3.checkParentStatus() // Should still be valid (different parent)
|
||||
|
||||
print("Step 5: Drop parent2 (affects child3)")
|
||||
parent2 = 0 // This should invalidate child3's reference
|
||||
|
||||
print("Step 6: Final check - all should be null now")
|
||||
child1.checkParentStatus() // Still null
|
||||
child2.checkParentStatus() // Still null
|
||||
child3.checkParentStatus() // Now null too
|
||||
|
||||
print("✅ Weak reference system validation complete!")
|
||||
return "All tests passed"
|
||||
}
|
||||
}
|
||||
@ -1,38 +0,0 @@
|
||||
// Simplified weak reference detection test
|
||||
|
||||
box Parent {
|
||||
init { child }
|
||||
|
||||
pack() {
|
||||
me.child = new Child()
|
||||
me.child.setParent(me) // This should detect weak assignment
|
||||
}
|
||||
|
||||
getChild() {
|
||||
return me.child
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p // Should detect weak field assignment
|
||||
}
|
||||
|
||||
checkParent() {
|
||||
return me.parent // Should detect weak field access
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
local p = new Parent()
|
||||
local child = p.getChild()
|
||||
|
||||
print("Testing weak field access...")
|
||||
local parent_ref = child.checkParent()
|
||||
|
||||
return "weak reference detection test completed"
|
||||
}
|
||||
}
|
||||
@ -1,37 +0,0 @@
|
||||
// 🔥 Weak-fini Prohibition Test - Should catch me.weakField.fini()
|
||||
|
||||
box SimpleResource {
|
||||
init { name }
|
||||
|
||||
pack(resourceName) {
|
||||
me.name = resourceName
|
||||
}
|
||||
}
|
||||
|
||||
box BadParent {
|
||||
init { weak weakChild }
|
||||
|
||||
pack() {
|
||||
me.weakChild = new SimpleResource("WeakChild")
|
||||
}
|
||||
|
||||
// This should trigger weak-fini prohibition
|
||||
fini() {
|
||||
print("🔥 BadParent.fini(): Attempting to finalize weak field")
|
||||
me.weakChild.fini() // Should fail: "Cannot finalize weak field 'weakChild'"
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== 🔥 Weak-fini Prohibition Test ===")
|
||||
|
||||
local badParent = new BadParent()
|
||||
print("BadParent created with weak child")
|
||||
|
||||
print("Attempting to finalize BadParent (should detect illegal weak-fini)...")
|
||||
badParent.fini() // Should fail during execution of user fini()
|
||||
|
||||
return "Test should have failed before reaching here"
|
||||
}
|
||||
}
|
||||
@ -1,62 +0,0 @@
|
||||
// Advanced weak reference auto-nil demonstration
|
||||
|
||||
box Parent {
|
||||
init { name, child }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
me.child = new Child()
|
||||
me.child.setParent(me) // This creates a weak reference
|
||||
}
|
||||
|
||||
getChild() {
|
||||
return me.child
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
getParentInfo() {
|
||||
// Check the weak reference
|
||||
return "Parent reference state checked"
|
||||
}
|
||||
|
||||
// Test method to manually check the weak field value
|
||||
checkWeakParent() {
|
||||
return me.parent
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== Weak Reference Auto-Nil Test ===")
|
||||
|
||||
local parent = new Parent("TestParent")
|
||||
local child = parent.getChild()
|
||||
|
||||
print("Step 1: Initial setup complete")
|
||||
print("Initial check: " + child.getParentInfo())
|
||||
|
||||
// Check initial weak reference value
|
||||
local parentRef = child.checkWeakParent()
|
||||
print("Initial parent ref exists: yes")
|
||||
|
||||
print("Step 2: Simulating parent 'drop' by setting to 0")
|
||||
parent = 0 // This should trigger weak reference invalidation
|
||||
|
||||
print("Step 3: Checking weak reference after parent drop")
|
||||
local parentRef2 = child.checkWeakParent()
|
||||
print("After drop parent ref exists: still checking")
|
||||
|
||||
return "weak reference lifecycle test completed"
|
||||
}
|
||||
}
|
||||
@ -1,50 +0,0 @@
|
||||
// Basic weak reference test case
|
||||
|
||||
box Parent {
|
||||
init { child }
|
||||
|
||||
pack() {
|
||||
me.child = new Child()
|
||||
me.child.setParent(me) // This should create a weak reference
|
||||
}
|
||||
|
||||
getChild() {
|
||||
return me.child
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
checkParent() {
|
||||
return me.parent != null
|
||||
}
|
||||
|
||||
getParentInfo() {
|
||||
if me.parent != null {
|
||||
return "Parent exists"
|
||||
} else {
|
||||
return "Parent is null (dropped)"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
local p = new Parent()
|
||||
local child = p.getChild()
|
||||
|
||||
print("Initial parent check: " + child.getParentInfo())
|
||||
|
||||
// When p goes out of scope, child.parent should automatically become null
|
||||
p = 0 // Setting to 0 instead of null to avoid the undefined variable issue
|
||||
|
||||
print("After parent dropped: " + child.getParentInfo())
|
||||
|
||||
return "weak reference test completed"
|
||||
}
|
||||
}
|
||||
@ -1,54 +0,0 @@
|
||||
// Complete weak reference auto-nil test
|
||||
|
||||
box Parent {
|
||||
init { name, child }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
me.child = new Child()
|
||||
me.child.setParent(me) // This should create a weak reference
|
||||
}
|
||||
|
||||
getChild() {
|
||||
return me.child
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
getParentInfo() {
|
||||
// Instead of comparing to null, check if parent field exists and is valid
|
||||
local parentExists = me.parent != 0 // Using 0 as a null check workaround
|
||||
if parentExists {
|
||||
return "Parent exists"
|
||||
} else {
|
||||
return "Parent is null (dropped)"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
local p = new Parent("TestParent")
|
||||
local child = p.getChild()
|
||||
|
||||
print("Initial: " + child.getParentInfo())
|
||||
|
||||
// Test the weak reference system
|
||||
// When p goes out of scope, child.parent should automatically become null
|
||||
p = 0 // Setting to 0 to simulate parent dropping
|
||||
|
||||
print("After drop: " + child.getParentInfo())
|
||||
|
||||
return "weak reference auto-nil test completed"
|
||||
}
|
||||
}
|
||||
@ -1,54 +0,0 @@
|
||||
// Simple direct test of weak reference auto-nil behavior
|
||||
|
||||
box Parent {
|
||||
init { name }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
// Direct access to weak field
|
||||
getParent() {
|
||||
return me.parent
|
||||
}
|
||||
|
||||
// Check if parent is null directly
|
||||
isParentNull() {
|
||||
local parentRef = me.parent
|
||||
print("Direct parent access returned: " + parentRef.toString())
|
||||
return parentRef
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== Simple Weak Reference Test ===")
|
||||
|
||||
local parent = new Parent("TestParent")
|
||||
local child = new Child()
|
||||
|
||||
print("Step 1: Set parent")
|
||||
child.setParent(parent)
|
||||
print("Parent before drop: " + child.getParent().toString())
|
||||
|
||||
print("Step 2: Drop parent")
|
||||
parent = 0 // This should trigger weak reference invalidation
|
||||
|
||||
print("Step 3: Check parent after drop")
|
||||
local parentAfterDrop = child.getParent()
|
||||
print("Parent after drop: " + parentAfterDrop.toString())
|
||||
|
||||
print("Step 4: Direct null check")
|
||||
child.isParentNull()
|
||||
|
||||
return "Simple test completed"
|
||||
}
|
||||
}
|
||||
@ -1,60 +0,0 @@
|
||||
// Working demonstration of weak reference auto-nil behavior
|
||||
|
||||
box Parent {
|
||||
init { name }
|
||||
|
||||
pack(parentName) {
|
||||
me.name = parentName
|
||||
}
|
||||
|
||||
getName() {
|
||||
return me.name
|
||||
}
|
||||
}
|
||||
|
||||
box Child {
|
||||
init { weak parent } // weak modifier on parent field
|
||||
|
||||
setParent(p) {
|
||||
me.parent = p
|
||||
}
|
||||
|
||||
getParentInfo() {
|
||||
// This method will use the weak field access system
|
||||
// which automatically returns null if the parent is dropped
|
||||
if me.parent == 0 {
|
||||
return "Parent is null (dropped)"
|
||||
} else {
|
||||
return "Parent exists"
|
||||
}
|
||||
}
|
||||
|
||||
// Direct weak field access for testing
|
||||
accessWeakParent() {
|
||||
return me.parent
|
||||
}
|
||||
}
|
||||
|
||||
static box Main {
|
||||
main() {
|
||||
print("=== Weak Reference Auto-Nil Demonstration ===")
|
||||
|
||||
local parent = new Parent("TestParent")
|
||||
local child = new Child()
|
||||
|
||||
print("Step 1: Setting up parent-child relationship")
|
||||
child.setParent(parent)
|
||||
print("After setup: " + child.getParentInfo())
|
||||
|
||||
print("Step 2: Simulating parent 'drop' (set to 0)")
|
||||
parent = 0 // This should trigger weak reference invalidation
|
||||
|
||||
print("Step 3: Checking child's parent reference after drop")
|
||||
print("After drop: " + child.getParentInfo())
|
||||
|
||||
print("Step 4: Direct weak field access test")
|
||||
local directAccess = child.accessWeakParent()
|
||||
|
||||
return "Auto-nil demonstration completed successfully"
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user