Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Object type wider support #850

Merged
merged 2 commits into from
Jul 18, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
100 changes: 100 additions & 0 deletions src/bscPlugin/validation/ScopeValidator.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,106 @@ describe('ScopeValidator', () => {
});

describe('argumentTypeMismatch', () => {
it('param `as object` supports all known types', () => {
program.setFile('source/file.bs', `
sub main()
consoleLog(Direction.up)
consoleLog(true)
consoleLog(main)
consoleLog(1.2)
consoleLog({} as Video)
consoleLog("test")
end sub
sub consoleLog(thing as object)
print thing
end sub
interface Video
url as string
end interface
enum Direction
up = "up"
down = "down"
end enum
`);
program.validate();
expectZeroDiagnostics(program);
});

it('`as object` var can be passed to various param types', () => {
program.setFile('source/file.bs', `
sub main()
obj = {} as object
printBoolean(obj)
printClass(obj)
printDouble(obj)
printEnum(obj)
printFloat(obj)
printFunction(obj)
printInteger(obj)
printInterface(obj)
printLongInteger(obj)
printString(obj)
end sub
sub printBoolean(value as boolean)
print value
end sub
class Person
name as string
end class
sub printClass(value as Person)
print value
end sub
sub printDouble(value as double)
print value
end sub
enum Direction
up = "up"
end enum
sub printEnum(value as Direction)
print value
end sub
sub printFloat(value as float)
print value
end sub
sub printFunction(value as function)
print value
end sub
interface Video
url as string
end interface
sub printInterface(value as Video)
print value
end sub
sub printInteger(value as integer)
print value
end sub
sub printLongInteger(value as LongInteger)
print value
end sub
sub printString(value as string)
print value
end sub
`);
program.validate();
expectZeroDiagnostics(program);
});


it('treats string enums as strings when assigned to string vars', () => {
program.setFile('source/file.bs', `
Expand Down
5 changes: 3 additions & 2 deletions src/types/BooleanType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isBooleanType, isDynamicType } from '../astUtils/reflection';
import { isBooleanType, isDynamicType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -16,7 +16,8 @@ export class BooleanType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isBooleanType(targetType) ||
isDynamicType(targetType)
isDynamicType(targetType) ||
isObjectType(targetType)
);
}

Expand Down
4 changes: 2 additions & 2 deletions src/types/ClassType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isClassType, isDynamicType } from '../astUtils/reflection';
import { isClassType, isDynamicType, isObjectType } from '../astUtils/reflection';
import type { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';
import { InheritableType } from './InheritableType';
Expand All @@ -14,7 +14,7 @@ export class ClassType extends InheritableType {
public isTypeCompatible(targetType: BscType) {
if (this.isEqual(targetType)) {
return true;
} else if (isDynamicType(targetType)) {
} else if (isDynamicType(targetType) || isObjectType(targetType)) {
return true;
} else if (isClassType(targetType)) {
return this.isTypeDescendent(targetType);
Expand Down
3 changes: 2 additions & 1 deletion src/types/DoubleType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType } from '../astUtils/reflection';
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -17,6 +17,7 @@ export class DoubleType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isDynamicType(targetType) ||
isObjectType(targetType) ||
isIntegerType(targetType) ||
isFloatType(targetType) ||
isDoubleType(targetType) ||
Expand Down
3 changes: 2 additions & 1 deletion src/types/EnumType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDynamicType, isEnumMemberType, isEnumType } from '../astUtils/reflection';
import { isDynamicType, isEnumMemberType, isEnumType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';
import { DynamicType } from './DynamicType';
Expand All @@ -19,6 +19,7 @@ export class EnumType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isDynamicType(targetType) ||
isObjectType(targetType) ||
this.isEqual(targetType) ||
(isEnumMemberType(targetType) && targetType?.enumName.toLowerCase() === this.name.toLowerCase())
);
Expand Down
3 changes: 2 additions & 1 deletion src/types/FloatType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType } from '../astUtils/reflection';
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -16,6 +16,7 @@ export class FloatType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isDynamicType(targetType) ||
isObjectType(targetType) ||
isIntegerType(targetType) ||
isFloatType(targetType) ||
isDoubleType(targetType) ||
Expand Down
7 changes: 5 additions & 2 deletions src/types/FunctionType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isFunctionType } from '../astUtils/reflection';
import { isDynamicType, isFunctionType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';
import { DynamicType } from './DynamicType';
Expand Down Expand Up @@ -39,7 +39,10 @@ export class FunctionType extends BscType {
}

public isTypeCompatible(targetType: BscType) {
if (targetType instanceof DynamicType) {
if (
isDynamicType(targetType) ||
isObjectType(targetType)
) {
return true;
}
return this.isEqual(targetType);
Expand Down
3 changes: 2 additions & 1 deletion src/types/IntegerType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType } from '../astUtils/reflection';
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -16,6 +16,7 @@ export class IntegerType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isDynamicType(targetType) ||
isObjectType(targetType) ||
isIntegerType(targetType) ||
isFloatType(targetType) ||
isDoubleType(targetType) ||
Expand Down
8 changes: 4 additions & 4 deletions src/types/InterfaceType.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { SymbolTypeFlag } from '../SymbolTable';
import { isDynamicType, isInterfaceType, isUnionType, isInheritableType } from '../astUtils/reflection';
import { isDynamicType, isInterfaceType, isUnionType, isInheritableType, isObjectType } from '../astUtils/reflection';
import type { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';
import { InheritableType } from './InheritableType';
Expand All @@ -15,11 +15,11 @@ export class InterfaceType extends InheritableType {
public readonly kind = BscTypeKind.InterfaceType;

public isTypeCompatible(targetType: BscType) {
//TODO: We need to make sure that things don't get assigned to built-in types
if (this.isEqual(targetType)) {
if (isDynamicType(targetType) || isObjectType(targetType)) {
return true;
}
if (isDynamicType(targetType)) {
//TODO: We need to make sure that things don't get assigned to built-in types
if (this.isEqual(targetType)) {
return true;
}
const ancestorTypes = this.getAncestorTypeList();
Expand Down
5 changes: 3 additions & 2 deletions src/types/InvalidType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDynamicType, isInvalidType } from '../astUtils/reflection';
import { isDynamicType, isInvalidType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -16,7 +16,8 @@ export class InvalidType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isInvalidType(targetType) ||
isDynamicType(targetType)
isDynamicType(targetType) ||
isObjectType(targetType)
);
}

Expand Down
3 changes: 2 additions & 1 deletion src/types/LongIntegerType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType } from '../astUtils/reflection';
import { isDoubleType, isDynamicType, isFloatType, isIntegerType, isLongIntegerType, isObjectType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -16,6 +16,7 @@ export class LongIntegerType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isDynamicType(targetType) ||
isObjectType(targetType) ||
isIntegerType(targetType) ||
isFloatType(targetType) ||
isDoubleType(targetType) ||
Expand Down
3 changes: 2 additions & 1 deletion src/types/StringType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDynamicType, isEnumMemberType, isEnumType, isStringType } from '../astUtils/reflection';
import { isDynamicType, isEnumMemberType, isEnumType, isObjectType, isStringType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -20,6 +20,7 @@ export class StringType extends BscType {
return (
isStringType(targetType) ||
isDynamicType(targetType) ||
isObjectType(targetType) ||
//string enums are compatible with strings
(
(isEnumType(targetType) || isEnumMemberType(targetType)) && isStringType(targetType.underlyingType)
Expand Down
4 changes: 2 additions & 2 deletions src/types/UnionType.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import type { GetTypeOptions } from '../interfaces';
import { isDynamicType, isUnionType } from '../astUtils/reflection';
import { isDynamicType, isObjectType, isUnionType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { ReferenceType } from './ReferenceType';
import { findTypeUnion, getUniqueType } from './helpers';
Expand Down Expand Up @@ -55,7 +55,7 @@ export class UnionType extends BscType {
}

isTypeCompatible(targetType: BscType): boolean {
if (isDynamicType(targetType)) {
if (isDynamicType(targetType) || isObjectType(targetType)) {
return true;
}
if (isUnionType(targetType)) {
Expand Down
5 changes: 3 additions & 2 deletions src/types/VoidType.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isDynamicType, isVoidType } from '../astUtils/reflection';
import { isDynamicType, isObjectType, isVoidType } from '../astUtils/reflection';
import { BscType } from './BscType';
import { BscTypeKind } from './BscTypeKind';

Expand All @@ -16,7 +16,8 @@ export class VoidType extends BscType {
public isTypeCompatible(targetType: BscType) {
return (
isVoidType(targetType) ||
isDynamicType(targetType)
isDynamicType(targetType) ||
isObjectType(targetType)
);
}

Expand Down